<commit_before>;(function ($, window, document, undefined) {
  'use strict';

  Foundation.libs.interchange = {
    name : 'interchange',

    version : '5.2.0',

    cache : {},

    images_loaded : false,
    nodes_loaded : false,

    settings : {
      load_attr : 'interchange',

      named_queries : {
        'default' : 'only screen',
        small : Foundation.media_queries.small,
        medium : Foundation.media_queries.medium,
        large : Foundation.media_queries.large,
        xlarge : Foundation.media_queries.xlarge,
        xxlarge: Foundation.media_queries.xxlarge,
        landscape : 'only screen and (orientation: landscape)',
        portrait : 'only screen and (orientation: portrait)',
        retina : 'only screen and (-webkit-min-device-pixel-ratio: 2),' +
          'only screen and (min--moz-device-pixel-ratio: 2),' +
          'only screen and (-o-min-device-pixel-ratio: 2/1),' +
          'only screen and (min-device-pixel-ratio: 2),' +
          'only screen and (min-resolution: 192dpi),' +
          'only screen and (min-resolution: 2dppx)'
      },

      directives : {
        replace: function (el, path, trigger) {
          // The trigger argument, if called within the directive, fires
          // an event named after the directive on the element, passing
          // any parameters along to the event that you pass to trigger.
          //
          // ex. trigger(), trigger([a, b, c]), or trigger(a, b, c)
          //
          // This allows you to bind a callback like so:
          // $('#interchangeContainer').on('replace', function (e, a, b, c) {
          //   console.log($(this).html(), a, b, c);
          // });

          if (/IMG/.test(el[0].nodeName)) {
            var orig_path = el[0].src;

            if (new RegExp(path, 'i').test(orig_path)) return;

            el[0].src = path;

            return trigger(el[0].src);
          }
          var last_path = el.data(this.data_attr + '-last-path');

          if (last_path == path) return;

          return $.get(path, function (response) {
            el.html(response);
            el.data(this.data_attr + '-last-path', path);
            trigger();
          });

        }
      }
    },

    init : function (scope, method, options) {
      Foundation.inherit(this, 'throttle random_str');

      this.data_attr = this.set_data_attr();
      $.extend(true, this.settings, method, options);

      this.bindings(method, options);
      this.load('images');
      this.load('nodes');
    },

    get_media_hash : function() {
        var mediaHash='';
        for (var queryName in this.settings.named_queries ) {
            mediaHash += matchMedia(this.settings.named_queries[queryName]).matches.toString();
        }
        return mediaHash;
    },

    events : function () {
      var self = this, prevMediaHash;

      $(window)
        .off('.interchange')
        .on('resize.fndtn.interchange', self.throttle(function () {
            var currMediaHash = self.get_media_hash();
            if (currMediaHash !== prevMediaHash) {
                self.resize();
            }
            prevMediaHash = currMediaHash;
        }, 50));

      return this;
    },

    resize : function () {
      var cache = this.cache;

      if(!this.images_loaded || !this.nodes_loaded) {
        setTimeout($.proxy(this.resize, this), 50);
        return;
      }

      for (var uuid in cache) {
        if (cache.hasOwnProperty(uuid)) {
          var passed = this.results(uuid, cache[uuid]);

          if (passed) {
            this.settings.directives[passed
              .scenario[1]].call(this, passed.el, passed.scenario[0], function () {
                if (arguments[0] instanceof Array) {
                  var args = arguments[0];
                } else {
                  var args = Array.prototype.slice.call(arguments, 0);
                }

                passed.el.trigger(passed.scenario[1], args);
              });
          }
        }
      }

    },

    results : function (uuid, scenarios) {
      var count = scenarios.length;

      if (count > 0) {
        var el = this.S('[' + this.add_namespace('data-uuid') + '="' + uuid + '"]');

        while (count--) {
          var mq, rule = scenarios[count][2];
          if (this.settings.named_queries.hasOwnProperty(rule)) {
            mq = matchMedia(this.settings.named_queries[rule]);
          } else {
            mq = matchMedia(rule);
          }
          if (mq.matches) {
            return {el: el, scenario: scenarios[count]};
          }
        }
      }

      return false;
    },

    load : function (type, force_update) {
      if (typeof this['cached_' + type] === 'undefined' || force_update) {
        this['update_' + type]();
      }

      return this['cached_' + type];
    },

    update_images : function () {
      var images = this.S('img[' + this.data_attr + ']'),
          count = images.length,
          i = count,
          loaded_count = 0,
          data_attr = this.data_attr;

      this.cache = {};
      this.cached_images = [];
      this.images_loaded = (count === 0);

      while (i--) {
        loaded_count++;
        if (images[i]) {
          var str = images[i].getAttribute(data_attr) || '';

          if (str.length > 0) {
            this.cached_images.push(images[i]);
          }
        }

        if (loaded_count === count) {
          this.images_loaded = true;
          this.enhance('images');
        }
      }

      return this;
    },

    update_nodes : function () {
      var nodes = this.S('[' + this.data_attr + ']').not('img'),
          count = nodes.length,
          i = count,
          loaded_count = 0,
          data_attr = this.data_attr;

      this.cached_nodes = [];
      // Set nodes_loaded to true if there are no nodes
      // this.nodes_loaded = false;
      this.nodes_loaded = (count === 0);

      while (i--) {
        loaded_count++;
        var str = nodes[i].getAttribute(data_attr) || '';

        if (str.length > 0) {
          this.cached_nodes.push(nodes[i]);
        }

        if(loaded_count === count) {
          this.nodes_loaded = true;
          this.enhance('nodes');
        }
      }

      return this;
    },

    enhance : function (type) {
      var i = this['cached_' + type].length;

      while (i--) {
        this.object($(this['cached_' + type][i]));
      }

      return $(window).trigger('resize');
    },

    parse_params : function (path, directive, mq) {
      return [this.trim(path), this.convert_directive(directive), this.trim(mq)];
    },

    convert_directive : function (directive) {
      var trimmed = this.trim(directive);

      if (trimmed.length > 0) {
        return trimmed;
      }

      return 'replace';
    },

    object : function(el) {
      var raw_arr = this.parse_data_attr(el),
          scenarios = [],
          i = raw_arr.length;

      if (i > 0) {
        while (i--) {
          var split = raw_arr[i].split(/\((.*?)(\))$/);

          if (split.length > 1) {
            var cached_split = split[0].split(','),
                params = this.parse_params(cached_split[0],
                  cached_split[1], split[1]);

            scenarios.push(params);
          }
        }
      }

      return this.store(el, scenarios);
    },

    uuid : function (separator) {
      var delim = separator || "-",
          self = this;

      function S4() {
        return self.random_str(6);
      }

      return (S4() + S4() + delim + S4() + delim + S4()
        + delim + S4() + delim + S4() + S4() + S4());
    },

    store : function (el, scenarios) {
      var uuid = this.uuid(),
          current_uuid = el.data(this.add_namespace('uuid', true));

      if (this.cache[current_uuid]) return this.cache[current_uuid];

      el.attr(this.add_namespace('data-uuid'), uuid);

      return this.cache[uuid] = scenarios;
    },

    trim : function(str) {
      if (typeof str === 'string') {
        return $.trim(str);
      }

      return str;
    },

    set_data_attr: function (init) {
      if (init) {
        if (this.namespace.length > 0) {
          return this.namespace + '-' + this.settings.load_attr;
        }

        return this.settings.load_attr;
      }

      if (this.namespace.length > 0) {
        return 'data-' + this.namespace + '-' + this.settings.load_attr;
      }

      return 'data-' + this.settings.load_attr;
    },

    parse_data_attr : function (el) {
      var raw = el.attr(this.attr_name()).split(/\[(.*?)\]/),
          i = raw.length,
          output = [];

      while (i--) {
        if (raw[i].replace(/[\W\d]+/, '').length > 4) {
          output.push(raw[i]);
        }
      }

      return output;
    },

    reflow : function () {
      this.load('images', true);
      this.load('nodes', true);
    }

  };

}(jQuery, this, this.document));
<commit_msg>Remove old uuid from interchange and use Foundation utils random_str() directly.<commit_after>;(function ($, window, document, undefined) {
  'use strict';

  Foundation.libs.interchange = {
    name : 'interchange',

    version : '5.2.0',

    cache : {},

    images_loaded : false,
    nodes_loaded : false,

    settings : {
      load_attr : 'interchange',

      named_queries : {
        'default' : 'only screen',
        small : Foundation.media_queries.small,
        medium : Foundation.media_queries.medium,
        large : Foundation.media_queries.large,
        xlarge : Foundation.media_queries.xlarge,
        xxlarge: Foundation.media_queries.xxlarge,
        landscape : 'only screen and (orientation: landscape)',
        portrait : 'only screen and (orientation: portrait)',
        retina : 'only screen and (-webkit-min-device-pixel-ratio: 2),' +
          'only screen and (min--moz-device-pixel-ratio: 2),' +
          'only screen and (-o-min-device-pixel-ratio: 2/1),' +
          'only screen and (min-device-pixel-ratio: 2),' +
          'only screen and (min-resolution: 192dpi),' +
          'only screen and (min-resolution: 2dppx)'
      },

      directives : {
        replace: function (el, path, trigger) {
          // The trigger argument, if called within the directive, fires
          // an event named after the directive on the element, passing
          // any parameters along to the event that you pass to trigger.
          //
          // ex. trigger(), trigger([a, b, c]), or trigger(a, b, c)
          //
          // This allows you to bind a callback like so:
          // $('#interchangeContainer').on('replace', function (e, a, b, c) {
          //   console.log($(this).html(), a, b, c);
          // });

          if (/IMG/.test(el[0].nodeName)) {
            var orig_path = el[0].src;

            if (new RegExp(path, 'i').test(orig_path)) return;

            el[0].src = path;

            return trigger(el[0].src);
          }
          var last_path = el.data(this.data_attr + '-last-path');

          if (last_path == path) return;

          return $.get(path, function (response) {
            el.html(response);
            el.data(this.data_attr + '-last-path', path);
            trigger();
          });

        }
      }
    },

    init : function (scope, method, options) {
      Foundation.inherit(this, 'throttle random_str');

      this.data_attr = this.set_data_attr();
      $.extend(true, this.settings, method, options);

      this.bindings(method, options);
      this.load('images');
      this.load('nodes');
    },

    get_media_hash : function() {
        var mediaHash='';
        for (var queryName in this.settings.named_queries ) {
            mediaHash += matchMedia(this.settings.named_queries[queryName]).matches.toString();
        }
        return mediaHash;
    },

    events : function () {
      var self = this, prevMediaHash;

      $(window)
        .off('.interchange')
        .on('resize.fndtn.interchange', self.throttle(function () {
            var currMediaHash = self.get_media_hash();
            if (currMediaHash !== prevMediaHash) {
                self.resize();
            }
            prevMediaHash = currMediaHash;
        }, 50));

      return this;
    },

    resize : function () {
      var cache = this.cache;

      if(!this.images_loaded || !this.nodes_loaded) {
        setTimeout($.proxy(this.resize, this), 50);
        return;
      }

      for (var uuid in cache) {
        if (cache.hasOwnProperty(uuid)) {
          var passed = this.results(uuid, cache[uuid]);

          if (passed) {
            this.settings.directives[passed
              .scenario[1]].call(this, passed.el, passed.scenario[0], function () {
                if (arguments[0] instanceof Array) {
                  var args = arguments[0];
                } else {
                  var args = Array.prototype.slice.call(arguments, 0);
                }

                passed.el.trigger(passed.scenario[1], args);
              });
          }
        }
      }

    },

    results : function (uuid, scenarios) {
      var count = scenarios.length;

      if (count > 0) {
        var el = this.S('[' + this.add_namespace('data-uuid') + '="' + uuid + '"]');

        while (count--) {
          var mq, rule = scenarios[count][2];
          if (this.settings.named_queries.hasOwnProperty(rule)) {
            mq = matchMedia(this.settings.named_queries[rule]);
          } else {
            mq = matchMedia(rule);
          }
          if (mq.matches) {
            return {el: el, scenario: scenarios[count]};
          }
        }
      }

      return false;
    },

    load : function (type, force_update) {
      if (typeof this['cached_' + type] === 'undefined' || force_update) {
        this['update_' + type]();
      }

      return this['cached_' + type];
    },

    update_images : function () {
      var images = this.S('img[' + this.data_attr + ']'),
          count = images.length,
          i = count,
          loaded_count = 0,
          data_attr = this.data_attr;

      this.cache = {};
      this.cached_images = [];
      this.images_loaded = (count === 0);

      while (i--) {
        loaded_count++;
        if (images[i]) {
          var str = images[i].getAttribute(data_attr) || '';

          if (str.length > 0) {
            this.cached_images.push(images[i]);
          }
        }

        if (loaded_count === count) {
          this.images_loaded = true;
          this.enhance('images');
        }
      }

      return this;
    },

    update_nodes : function () {
      var nodes = this.S('[' + this.data_attr + ']').not('img'),
          count = nodes.length,
          i = count,
          loaded_count = 0,
          data_attr = this.data_attr;

      this.cached_nodes = [];
      // Set nodes_loaded to true if there are no nodes
      // this.nodes_loaded = false;
      this.nodes_loaded = (count === 0);

      while (i--) {
        loaded_count++;
        var str = nodes[i].getAttribute(data_attr) || '';

        if (str.length > 0) {
          this.cached_nodes.push(nodes[i]);
        }

        if(loaded_count === count) {
          this.nodes_loaded = true;
          this.enhance('nodes');
        }
      }

      return this;
    },

    enhance : function (type) {
      var i = this['cached_' + type].length;

      while (i--) {
        this.object($(this['cached_' + type][i]));
      }

      return $(window).trigger('resize');
    },

    parse_params : function (path, directive, mq) {
      return [this.trim(path), this.convert_directive(directive), this.trim(mq)];
    },

    convert_directive : function (directive) {
      var trimmed = this.trim(directive);

      if (trimmed.length > 0) {
        return trimmed;
      }

      return 'replace';
    },

    object : function(el) {
      var raw_arr = this.parse_data_attr(el),
          scenarios = [],
          i = raw_arr.length;

      if (i > 0) {
        while (i--) {
          var split = raw_arr[i].split(/\((.*?)(\))$/);

          if (split.length > 1) {
            var cached_split = split[0].split(','),
                params = this.parse_params(cached_split[0],
                  cached_split[1], split[1]);

            scenarios.push(params);
          }
        }
      }

      return this.store(el, scenarios);
    },

    store : function (el, scenarios) {
      var uuid = this.random_str(),
          current_uuid = el.data(this.add_namespace('uuid', true));

      if (this.cache[current_uuid]) return this.cache[current_uuid];

      el.attr(this.add_namespace('data-uuid'), uuid);

      return this.cache[uuid] = scenarios;
    },

    trim : function(str) {
      if (typeof str === 'string') {
        return $.trim(str);
      }

      return str;
    },

    set_data_attr: function (init) {
      if (init) {
        if (this.namespace.length > 0) {
          return this.namespace + '-' + this.settings.load_attr;
        }

        return this.settings.load_attr;
      }

      if (this.namespace.length > 0) {
        return 'data-' + this.namespace + '-' + this.settings.load_attr;
      }

      return 'data-' + this.settings.load_attr;
    },

    parse_data_attr : function (el) {
      var raw = el.attr(this.attr_name()).split(/\[(.*?)\]/),
          i = raw.length,
          output = [];

      while (i--) {
        if (raw[i].replace(/[\W\d]+/, '').length > 4) {
          output.push(raw[i]);
        }
      }

      return output;
    },

    reflow : function () {
      this.load('images', true);
      this.load('nodes', true);
    }

  };

}(jQuery, this, this.document));
<|endoftext|>


<commit_before>/**
 * Admin
 *
 * for admin pages
 */
var Admin = typeof Admin == 'undefined' ? {} : Admin;

/**
 * Gets spinner class
 */
Admin.spinnerClass = function() {
	return Admin.iconClass('spinner') + ' ' +Admin.iconClass('spin', false);
}

/**
 * Forms
 *
 * @return void
 */
Admin.form = function() {
	// Tooltips activation
	$('[rel=tooltip],*[data-title]:not([data-content]),input[title],textarea[title]').tooltip();
	if (typeof $.prototype.tipsy == 'function') {
		$('a.tooltip').tipsy({gravity: 's', html: false}); // Legacy tooltip
	}

	var ajaxToggle = function(e) {
		var $this = $(this);
		var spinnerClass = Admin.spinnerClass();
		$this.addClass(spinnerClass).find('i').attr('class', 'icon-none');
		var url = $this.data('url');
		$.post(url, function(data) {
			$this.parent().html(data);
		});
	}

	// Autocomplete
	if (typeof $.fn.typeahead_autocomplete === 'function') {
		$('input.typeahead-autocomplete').typeahead_autocomplete();
	}

	// Row Actions
	$('body')
		.on('click', 'a[data-row-action]', Admin.processLink)
		.on('click', 'a.ajax-toggle', ajaxToggle)
	;
}

/**
 * Protect forms for accidental page refresh
 */
Admin.protectForms = function() {
	var forms  = document.getElementsByClassName('protected-form');
	if (forms.length > 0) {
		var watchElements = ['input', 'select', 'textarea'];
		var ignored = ['button', '[type=submit]', '.cancel'];
		for (var i = 0; i < forms.length; i++) {
			var $form = $(forms[i]);
			var customIgnore = $form.data('ignore-elements');
			var whitelist = ignored.join(',');
			if (customIgnore) {
				whitelist += ',' + customIgnore;
			}
			$form
				.on('change', watchElements.join(','), function(e) {
					$form.data('dirty', true);
				})
				.on('click', whitelist, function(e) {
					$form.data('dirty', false);
					Croogo.Wysiwyg.resetDirty();
				});
		}

		window.onbeforeunload = function(e) {
			var dirty = false;
			for (var i = 0; i < forms.length; i++) {
				if ($(forms[i]).data('dirty') === true) {
					dirty = true;
					break;
				}
			}
			if (!dirty && !Croogo.Wysiwyg.checkDirty()) {
				return;
			}

			var confirmationMessage = 'Please save your changes';
			(e || window.event).returnValue = confirmationMessage;
			return confirmationMessage;
		};
	}
}

/**
 * Helper to process row action links
 */
Admin.processLink = function(event) {
	var $el = $(event.currentTarget);
	var checkbox = $(event.currentTarget.attributes["href"].value);
	var form = checkbox.get(0).form;
	var action = $el.data('row-action');
	var confirmMessage = $el.data('confirm-message');
	if (confirmMessage && !confirm(confirmMessage)) {
		return false;
	}
	$('input[type=checkbox]', form).prop('checked', false);
	checkbox.prop("checked", true);
	$('#bulk-action select', form).val(action);
	form.submit();
	return false;
}

/**
 * Extra stuff
 *
 * rounded corners, striped table rows, etc
 *
 * @return void
 */
Admin.extra = function() {
	var hash = document.location.hash;
	var $tabs = $('#content .nav-tabs');
	if (hash && hash.match("^#tab_")) {
		// Activates tab if hash starting with tab_* is given
		$tabs.find('a[href=' + hash.replace('tab_', '') + ']').tab('show');
	} else {
		// Activates the first tab in #content by default
		$tabs.find('li:first-child a').tab('show');
	}

	// Apply buttons jump to current tab for persistence
	$('#content [name="apply"]').click(function() {
		var activeTab = $tabs.find('.active [data-toggle=tab]').attr('href');
		var form = $('#content form:first');
		var action = form.attr('action').split('#')[0];
		form.attr('action', action + activeTab.replace('#', '#tab_'));
	});

	if (typeof $.prototype.tabs == 'function') {
		$('.tabs').tabs(); // legacy tabs from jquery-ui
	}
	if (typeof $.prototype.elastic == 'function') {
		$('textarea').not('.content').elastic();
	}
	$("div.message").addClass("notice");
	$('#loading p').addClass('ui-corner-bl ui-corner-br');
}

/**
 * Initialize boxes to enable to toggling Box content
 */
Admin.slideBoxToggle = function() {
	var iconMinus = Admin.iconClass('minus', false);
	var iconPlus = Admin.iconClass('plus', false);
	$('body').on('click', '.box-title', function() {
		$(this)
			.next().slideToggle(function() {
				$(this).trigger('slide.toggle');
			}).end()
			.find(iconMinus)
			.switchClass(iconMinus, iconPlus).end()
			.find(iconPlus)
			.switchClass(iconPlus, iconMinus);
	});
};

/**
 * Helper callback for toggling record selection
 */
Admin.toggleRowSelection = function(selector, checkboxSelector) {
	var $selector = $(selector);
	if (typeof checkboxSelector == 'undefined') {
		checkboxSelector = "input.row-select[type='checkbox']";
	}
	$selector.on('click', function(e) {
		$(checkboxSelector).prop('checked', $selector.is(':checked'));
	});
}

/**
 * Helper method to get the proper icon class name based on theme settings
 */
Admin.iconClass = function(icon, includeDefault) {
	var result = '';
	if (typeof Croogo.themeSettings.icons[icon] === 'string') {
		icon = Croogo.themeSettings.icons[icon];
	}
	if (typeof includeDefault === 'undefined') {
		includeDefault = true;
	}
	if (includeDefault) {
		result = Croogo.themeSettings.iconDefaults['classDefault'] + ' ';
	}
	result += Croogo.themeSettings.iconDefaults['classPrefix'] + icon;
	return result.trim();
}
<commit_msg>Fix: check for presence of Croogo.Wysiwyg object<commit_after>/**
 * Admin
 *
 * for admin pages
 */
var Admin = typeof Admin == 'undefined' ? {} : Admin;

/**
 * Gets spinner class
 */
Admin.spinnerClass = function() {
	return Admin.iconClass('spinner') + ' ' +Admin.iconClass('spin', false);
}

/**
 * Forms
 *
 * @return void
 */
Admin.form = function() {
	// Tooltips activation
	$('[rel=tooltip],*[data-title]:not([data-content]),input[title],textarea[title]').tooltip();
	if (typeof $.prototype.tipsy == 'function') {
		$('a.tooltip').tipsy({gravity: 's', html: false}); // Legacy tooltip
	}

	var ajaxToggle = function(e) {
		var $this = $(this);
		var spinnerClass = Admin.spinnerClass();
		$this.addClass(spinnerClass).find('i').attr('class', 'icon-none');
		var url = $this.data('url');
		$.post(url, function(data) {
			$this.parent().html(data);
		});
	}

	// Autocomplete
	if (typeof $.fn.typeahead_autocomplete === 'function') {
		$('input.typeahead-autocomplete').typeahead_autocomplete();
	}

	// Row Actions
	$('body')
		.on('click', 'a[data-row-action]', Admin.processLink)
		.on('click', 'a.ajax-toggle', ajaxToggle)
	;
}

/**
 * Protect forms for accidental page refresh
 */
Admin.protectForms = function() {
	var forms  = document.getElementsByClassName('protected-form');
	if (forms.length > 0) {
		var watchElements = ['input', 'select', 'textarea'];
		var ignored = ['button', '[type=submit]', '.cancel'];
		for (var i = 0; i < forms.length; i++) {
			var $form = $(forms[i]);
			var customIgnore = $form.data('ignore-elements');
			var whitelist = ignored.join(',');
			if (customIgnore) {
				whitelist += ',' + customIgnore;
			}
			$form
				.on('change', watchElements.join(','), function(e) {
					$form.data('dirty', true);
				})
				.on('click', whitelist, function(e) {
					$form.data('dirty', false);
					if (Croogo.Wysiwyg) {
						Croogo.Wysiwyg.resetDirty();
					}
				});
		}

		window.onbeforeunload = function(e) {
			var dirty = false;
			for (var i = 0; i < forms.length; i++) {
				if ($(forms[i]).data('dirty') === true) {
					dirty = true;
					break;
				}
			}
			var Wysiwyg = Croogo.Wysiwyg;
			if (!dirty && (Wysiwyg.checkDirty && !Wysiwyg.checkDirty())) {
				return;
			}

			var confirmationMessage = 'Please save your changes';
			(e || window.event).returnValue = confirmationMessage;
			return confirmationMessage;
		};
	}
}

/**
 * Helper to process row action links
 */
Admin.processLink = function(event) {
	var $el = $(event.currentTarget);
	var checkbox = $(event.currentTarget.attributes["href"].value);
	var form = checkbox.get(0).form;
	var action = $el.data('row-action');
	var confirmMessage = $el.data('confirm-message');
	if (confirmMessage && !confirm(confirmMessage)) {
		return false;
	}
	$('input[type=checkbox]', form).prop('checked', false);
	checkbox.prop("checked", true);
	$('#bulk-action select', form).val(action);
	form.submit();
	return false;
}

/**
 * Extra stuff
 *
 * rounded corners, striped table rows, etc
 *
 * @return void
 */
Admin.extra = function() {
	var hash = document.location.hash;
	var $tabs = $('#content .nav-tabs');
	if (hash && hash.match("^#tab_")) {
		// Activates tab if hash starting with tab_* is given
		$tabs.find('a[href=' + hash.replace('tab_', '') + ']').tab('show');
	} else {
		// Activates the first tab in #content by default
		$tabs.find('li:first-child a').tab('show');
	}

	// Apply buttons jump to current tab for persistence
	$('#content [name="apply"]').click(function() {
		var activeTab = $tabs.find('.active [data-toggle=tab]').attr('href');
		var form = $('#content form:first');
		var action = form.attr('action').split('#')[0];
		form.attr('action', action + activeTab.replace('#', '#tab_'));
	});

	if (typeof $.prototype.tabs == 'function') {
		$('.tabs').tabs(); // legacy tabs from jquery-ui
	}
	if (typeof $.prototype.elastic == 'function') {
		$('textarea').not('.content').elastic();
	}
	$("div.message").addClass("notice");
	$('#loading p').addClass('ui-corner-bl ui-corner-br');
}

/**
 * Initialize boxes to enable to toggling Box content
 */
Admin.slideBoxToggle = function() {
	var iconMinus = Admin.iconClass('minus', false);
	var iconPlus = Admin.iconClass('plus', false);
	$('body').on('click', '.box-title', function() {
		$(this)
			.next().slideToggle(function() {
				$(this).trigger('slide.toggle');
			}).end()
			.find(iconMinus)
			.switchClass(iconMinus, iconPlus).end()
			.find(iconPlus)
			.switchClass(iconPlus, iconMinus);
	});
};

/**
 * Helper callback for toggling record selection
 */
Admin.toggleRowSelection = function(selector, checkboxSelector) {
	var $selector = $(selector);
	if (typeof checkboxSelector == 'undefined') {
		checkboxSelector = "input.row-select[type='checkbox']";
	}
	$selector.on('click', function(e) {
		$(checkboxSelector).prop('checked', $selector.is(':checked'));
	});
}

/**
 * Helper method to get the proper icon class name based on theme settings
 */
Admin.iconClass = function(icon, includeDefault) {
	var result = '';
	if (typeof Croogo.themeSettings.icons[icon] === 'string') {
		icon = Croogo.themeSettings.icons[icon];
	}
	if (typeof includeDefault === 'undefined') {
		includeDefault = true;
	}
	if (includeDefault) {
		result = Croogo.themeSettings.iconDefaults['classDefault'] + ' ';
	}
	result += Croogo.themeSettings.iconDefaults['classPrefix'] + icon;
	return result.trim();
}
<|endoftext|>


<commit_before>// Copyright (c) IPython Development Team.
// Distributed under the terms of the Modified BSD License.

require([
    'base/js/namespace',
    'jquery',
    'notebook/js/notebook',
    'contents',
    'base/js/utils',
    'base/js/page',
    'notebook/js/layoutmanager',
    'base/js/events',
    'auth/js/loginwidget',
    'notebook/js/maintoolbar',
    'notebook/js/pager',
    'notebook/js/quickhelp',
    'notebook/js/menubar',
    'notebook/js/notificationarea',
    'notebook/js/savewidget',
    'notebook/js/actions',
    'notebook/js/keyboardmanager',
    'notebook/js/config',
    'notebook/js/kernelselector',
    'codemirror/lib/codemirror',
    'notebook/js/about',
    // only loaded, not used, please keep sure this is loaded last
    'custom/custom'
], function(
    IPython,
    $,
    notebook,
    contents,
    utils,
    page,
    layoutmanager,
    events,
    loginwidget,
    maintoolbar,
    pager,
    quickhelp,
    menubar,
    notificationarea,
    savewidget,
    actions,
    keyboardmanager,
    config,
    kernelselector,
    CodeMirror,
    about,
    // please keep sure that even if not used, this is loaded last
    custom
    ) {
    "use strict";

    // compat with old IPython, remove for IPython > 3.0
    window.CodeMirror = CodeMirror;

    var common_options = {
        ws_url : utils.get_body_data("wsUrl"),
        base_url : utils.get_body_data("baseUrl"),
        notebook_path : utils.get_body_data("notebookPath"),
        notebook_name : utils.get_body_data('notebookName')
    };

    var user_config = $.extend({}, config.default_config);
    var page = new page.Page();
    var layout_manager = new layoutmanager.LayoutManager();
    var pager = new pager.Pager('div#pager', 'div#pager_splitter', {
        layout_manager: layout_manager,
        events: events});
    var acts = new actions.init();
    var keyboard_manager = new keyboardmanager.KeyboardManager({
        pager: pager,
        events: events,
        actions: acts });
    var save_widget = new savewidget.SaveWidget('span#save_widget', {
        events: events,
        keyboard_manager: keyboard_manager});
    var contents = new contents.Contents($.extend({
        events: events},
        common_options));
    var notebook = new notebook.Notebook('div#notebook', $.extend({
        events: events,
        keyboard_manager: keyboard_manager,
        save_widget: save_widget,
        contents: contents,
        config: user_config},
        common_options));
    var login_widget = new loginwidget.LoginWidget('span#login_widget', common_options);
    var toolbar = new maintoolbar.MainToolBar('#maintoolbar-container', {
        notebook: notebook,
        events: events,
        actions: acts});
    var quick_help = new quickhelp.QuickHelp({
        keyboard_manager: keyboard_manager,
        events: events,
        notebook: notebook});
    keyboard_manager.set_notebook(notebook);
    keyboard_manager.set_quickhelp(quick_help);
    var menubar = new menubar.MenuBar('#menubar', $.extend({
        notebook: notebook,
        contents: contents,
        layout_manager: layout_manager,
        events: events,
        save_widget: save_widget,
        quick_help: quick_help},
        common_options));
    var notification_area = new notificationarea.NotebookNotificationArea(
        '#notification_area', {
        events: events,
        save_widget: save_widget,
        notebook: notebook,
        keyboard_manager: keyboard_manager});
    notification_area.init_notification_widgets();
    var kernel_selector = new kernelselector.KernelSelector(
        '#kernel_selector_widget', notebook);

    $('body').append('

x'+
                     'x'+
                     'x

');
    var nh = $('#test1').innerHeight();
    var bh = $('#test2').innerHeight();
    var ih = $('#test3').innerHeight();
    if(nh != bh || nh != ih) {
        $('head').append('');
    }
    $('#fonttest').remove();

    page.show();

    layout_manager.do_resize();
    var first_load = function () {
        layout_manager.do_resize();
        var hash = document.location.hash;
        if (hash) {
            document.location.hash = '';
            document.location.hash = hash;
        }
        notebook.set_autosave_interval(notebook.minimum_autosave_interval);
        // only do this once
        events.off('notebook_loaded.Notebook', first_load);
    };
    events.on('notebook_loaded.Notebook', first_load);

    IPython.page = page;
    IPython.layout_manager = layout_manager;
    IPython.notebook = notebook;
    IPython.contents = contents;
    IPython.pager = pager;
    IPython.quick_help = quick_help;
    IPython.login_widget = login_widget;
    IPython.menubar = menubar;
    IPython.toolbar = toolbar;
    IPython.notification_area = notification_area;
    IPython.keyboard_manager = keyboard_manager;
    IPython.save_widget = save_widget;
    IPython.config = user_config;
    IPython.tooltip = notebook.tooltip;

    events.trigger('app_initialized.NotebookApp');
    notebook.load_notebook(common_options.notebook_path);

});
<commit_msg>Load nbextensions from config<commit_after>// Copyright (c) IPython Development Team.
// Distributed under the terms of the Modified BSD License.

require([
    'base/js/namespace',
    'jquery',
    'notebook/js/notebook',
    'contents',
    'services/config',
    'base/js/utils',
    'base/js/page',
    'notebook/js/layoutmanager',
    'base/js/events',
    'auth/js/loginwidget',
    'notebook/js/maintoolbar',
    'notebook/js/pager',
    'notebook/js/quickhelp',
    'notebook/js/menubar',
    'notebook/js/notificationarea',
    'notebook/js/savewidget',
    'notebook/js/actions',
    'notebook/js/keyboardmanager',
    'notebook/js/config',
    'notebook/js/kernelselector',
    'codemirror/lib/codemirror',
    'notebook/js/about',
    // only loaded, not used, please keep sure this is loaded last
    'custom/custom'
], function(
    IPython,
    $,
    notebook,
    contents,
    configmod,
    utils,
    page,
    layoutmanager,
    events,
    loginwidget,
    maintoolbar,
    pager,
    quickhelp,
    menubar,
    notificationarea,
    savewidget,
    actions,
    keyboardmanager,
    config,
    kernelselector,
    CodeMirror,
    about,
    // please keep sure that even if not used, this is loaded last
    custom
    ) {
    "use strict";

    // compat with old IPython, remove for IPython > 3.0
    window.CodeMirror = CodeMirror;

    var common_options = {
        ws_url : utils.get_body_data("wsUrl"),
        base_url : utils.get_body_data("baseUrl"),
        notebook_path : utils.get_body_data("notebookPath"),
        notebook_name : utils.get_body_data('notebookName')
    };

    var user_config = $.extend({}, config.default_config);
    var page = new page.Page();
    var layout_manager = new layoutmanager.LayoutManager();
    var pager = new pager.Pager('div#pager', 'div#pager_splitter', {
        layout_manager: layout_manager,
        events: events});
    var acts = new actions.init();
    var keyboard_manager = new keyboardmanager.KeyboardManager({
        pager: pager,
        events: events,
        actions: acts });
    var save_widget = new savewidget.SaveWidget('span#save_widget', {
        events: events,
        keyboard_manager: keyboard_manager});
    var contents = new contents.Contents($.extend({
        events: events},
        common_options));
    var config_section = new configmod.ConfigSection('notebook', common_options);
    config_section.load();
    var notebook = new notebook.Notebook('div#notebook', $.extend({
        events: events,
        keyboard_manager: keyboard_manager,
        save_widget: save_widget,
        contents: contents,
        config: user_config},
        common_options));
    var login_widget = new loginwidget.LoginWidget('span#login_widget', common_options);
    var toolbar = new maintoolbar.MainToolBar('#maintoolbar-container', {
        notebook: notebook,
        events: events,
        actions: acts});
    var quick_help = new quickhelp.QuickHelp({
        keyboard_manager: keyboard_manager,
        events: events,
        notebook: notebook});
    keyboard_manager.set_notebook(notebook);
    keyboard_manager.set_quickhelp(quick_help);
    var menubar = new menubar.MenuBar('#menubar', $.extend({
        notebook: notebook,
        contents: contents,
        layout_manager: layout_manager,
        events: events,
        save_widget: save_widget,
        quick_help: quick_help},
        common_options));
    var notification_area = new notificationarea.NotebookNotificationArea(
        '#notification_area', {
        events: events,
        save_widget: save_widget,
        notebook: notebook,
        keyboard_manager: keyboard_manager});
    notification_area.init_notification_widgets();
    var kernel_selector = new kernelselector.KernelSelector(
        '#kernel_selector_widget', notebook);

    $('body').append('

x'+
                     'x'+
                     'x

');
    var nh = $('#test1').innerHeight();
    var bh = $('#test2').innerHeight();
    var ih = $('#test3').innerHeight();
    if(nh != bh || nh != ih) {
        $('head').append('');
    }
    $('#fonttest').remove();

    page.show();

    layout_manager.do_resize();
    var first_load = function () {
        layout_manager.do_resize();
        var hash = document.location.hash;
        if (hash) {
            document.location.hash = '';
            document.location.hash = hash;
        }
        notebook.set_autosave_interval(notebook.minimum_autosave_interval);
        // only do this once
        events.off('notebook_loaded.Notebook', first_load);
    };
    events.on('notebook_loaded.Notebook', first_load);

    IPython.page = page;
    IPython.layout_manager = layout_manager;
    IPython.notebook = notebook;
    IPython.contents = contents;
    IPython.pager = pager;
    IPython.quick_help = quick_help;
    IPython.login_widget = login_widget;
    IPython.menubar = menubar;
    IPython.toolbar = toolbar;
    IPython.notification_area = notification_area;
    IPython.keyboard_manager = keyboard_manager;
    IPython.save_widget = save_widget;
    IPython.config = user_config;
    IPython.tooltip = notebook.tooltip;

    events.trigger('app_initialized.NotebookApp');
    config_section.loaded.then(function() {
        if (config_section.data.load_extensions) {
            var nbextension_paths = Object.getOwnPropertyNames(
                                        config_section.data.load_extensions);
            IPython.load_extensions.apply(this, nbextension_paths);
        }
    });
    notebook.load_notebook(common_options.notebook_path);

});
<|endoftext|>


<commit_before>Components.utils.import('resource://greasemonkey/util.js'); // ref'd in XUL

var gScriptId = decodeURIComponent(location.hash.substring(1));
var gScript = GM_util.getService().config.getMatchingScripts(function(script) {
  return script && (script.id == gScriptId);
})[0];

var gScriptExcludesEl;
var gScriptIncludesEl;
var gTabboxEl;
var gUserExcludesEl;
var gUserIncludesEl;
var gUserTabEl;

window.addEventListener('load', function() {
  // I wanted "%s" but % is reserved in a DTD and I don't know the literal.
  document.title = document.title.replace('!!', gScript.localized.name);

  var gTabboxEl = document.getElementsByTagName('tabbox')[0];
  gUserTabEl = gTabboxEl.tabs.getItemAtIndex(0);

  gUserIncludesEl = document.getElementById('user-includes');
  gUserExcludesEl = document.getElementById('user-excludes');
  gScriptIncludesEl = document.getElementById('script-includes');
  gScriptExcludesEl = document.getElementById('script-excludes');

  gScriptIncludesEl.pages = gScript.includes;
  gScriptIncludesEl.onAddUserExclude = function(url) {
    gUserExcludesEl.addPage(url);
    gTabboxEl.selectedTab = gUserTabEl;
  };
  gUserIncludesEl.pages = gScript.userIncludes;

  gScriptExcludesEl.pages = gScript.excludes;
  gScriptExcludesEl.onAddUserInclude = function(url) {
    gUserIncludesEl.addPage(url);
    gTabboxEl.selectedTab = gUserTabEl;
  };
  gUserExcludesEl.pages = gScript.userExcludes;
}, false);

function onDialogAccept() {
  gScript.includes = gScriptIncludesEl.pages;
  gScript.userIncludes = gUserIncludesEl.pages;
  gScript.excludes = gScriptExcludesEl.pages;
  gScript.userExcludes = gUserExcludesEl.pages;
  GM_util.getService().config._changed(gScript, "cludes");
}
<commit_msg>Update scriptprefs.js<commit_after>Components.utils.import('resource://greasemonkey/util.js'); // ref'd in XUL

var gScriptId = decodeURIComponent(location.hash.substring(1));
var gScript = GM_util.getService().config.getMatchingScripts(function(script) {
  return script && (script.id == gScriptId);
})[0];

var gScriptExcludesEl;
var gScriptMatchesEl;
var gScriptIncludesEl;
var gTabboxEl;
var gUserExcludesEl;
var gUserMatchesEl;
var gUserIncludesEl;
var gUserTabEl;

window.addEventListener('load', function() {
  // I wanted "%s" but % is reserved in a DTD and I don't know the literal.
  document.title = document.title.replace('!!', gScript.localized.name);

  var gTabboxEl = document.getElementsByTagName('tabbox')[0];
  gUserTabEl = gTabboxEl.tabs.getItemAtIndex(0);

  gUserIncludesEl = document.getElementById('user-includes');
  gUserMatchesEl = document.getElementById('user-matches');
  gUserExcludesEl = document.getElementById('user-excludes');
  gScriptIncludesEl = document.getElementById('script-includes');
  gScriptMatchesEl = document.getElementById('script-matches');
  gScriptExcludesEl = document.getElementById('script-excludes');

  gScriptIncludesEl.pages = gScript.includes;
  gScriptIncludesEl.onAddUserExclude = function(url) {
    gUserExcludesEl.addPage(url);
    gTabboxEl.selectedTab = gUserTabEl;
  };
  gUserIncludesEl.pages = gScript.userIncludes;

  for (var i = 0; i < gScript.matches.length; i++) {
    gScriptMatchesEl.addPage(gScript.matches[i].pattern);
  }
  /*
  gScriptMatchesEl.onAddUserExclude = function(url) {
    gUserExcludeEl.addPage(url);
    gTabboxEl.selectedTab = gUserTabEl;
  };
  */
  for (var i = 0; i < gScript.userMatches.length; i++) {
    gUserMatchesEl.addPage(gScript.userMatches[i].pattern);
  }

  gScriptExcludesEl.pages = gScript.excludes;
  gScriptExcludesEl.onAddUserInclude = function(url) {
    gUserIncludesEl.addPage(url);
    gTabboxEl.selectedTab = gUserTabEl;
  };
  gUserExcludesEl.pages = gScript.userExcludes;
}, false);

function onDialogAccept() {
  gScript.includes = gScriptIncludesEl.pages;
  gScript.userIncludes = gUserIncludesEl.pages;
  gScript.matches = gScriptMatchesEl.pages;
  gScript.userMatches = gUserMatchesEl.pages;
  gScript.excludes = gScriptExcludesEl.pages;
  gScript.userExcludes = gUserExcludesEl.pages;
  GM_util.getService().config._changed(gScript, "cludes");
}
<|endoftext|>


<commit_before>//=============================================================================
//  MuseScore
//  Linux Music Score Editor
//  $Id:$
//
//  Test plugin
//
//  Copyright (C)2009 Werner Schweer and others
//
//  This program is free software; you can redistribute it and/or modify
//  it under the terms of the GNU General Public License version 2.
//
//  This program is distributed in the hope that it will be useful,
//  but WITHOUT ANY WARRANTY; without even the implied warranty of
//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
//  GNU General Public License for more details.
//
//  You should have received a copy of the GNU General Public License
//  along with this program; if not, write to the Free Software
//  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
//=============================================================================

//
// error handling is mostly omitted!
//

//---------------------------------------------------------
//    init
//---------------------------------------------------------

function init()
      {
      };

var form;

//---------------------------------------------------------
//    run
//    remove all but the first notes from all chords
//---------------------------------------------------------

function run()
{
      var score = curScore;
      var cursor = new Cursor(curScore);
      var selectionEnd = new Cursor(curScore);
      cursor.goToSelectionStart();
      selectionEnd.goToSelectionEnd();

      var startStaff = cursor.staff;
      var endStaff = selectionEnd.staff;

      for (var staff = startStaff; staff<endStaff; ++staff) {
          cursor.goToSelectionStart();
          for (var v=0; v<4; v++) {
              cursor.goToSelectionStart();
              cursor.voice = v;
              cursor.staff = staff;

              while (cursor.tick() < selectionEnd.tick()) {
                    if (cursor.isChord()) {
                       var chord = cursor.chord();
                       if (chord.notes>1) {
                           for (var i = 0; i<chord.notes; i++) {
                              var note = chord.note(i);
                              chord.removeNote(i);
                           }
                        }
                    }
              cursor.next();
              }
        }
      }
}
var mscorePlugin = {
      majorVersion: 0,
      minorVersion: 1,
      menu: 'Plugins.Zap Chords',
      init: init,
      run:  run
      };

mscorePlugin;

<commit_msg>fixed comment<commit_after>//=============================================================================
//  MuseScore
//  Linux Music Score Editor
//  $Id:$
//
//  Zap Chords plugin
//
//  Copyright (C)2009 Werner Schweer and others
//
//  This program is free software; you can redistribute it and/or modify
//  it under the terms of the GNU General Public License version 2.
//
//  This program is distributed in the hope that it will be useful,
//  but WITHOUT ANY WARRANTY; without even the implied warranty of
//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
//  GNU General Public License for more details.
//
//  You should have received a copy of the GNU General Public License
//  along with this program; if not, write to the Free Software
//  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
//=============================================================================

//
// error handling is mostly omitted!
//

//---------------------------------------------------------
//    init
//---------------------------------------------------------

function init()
      {
      };

var form;

//---------------------------------------------------------
//    run
//    remove all but the first notes from all chords
//---------------------------------------------------------

function run()
{
      var score = curScore;
      var cursor = new Cursor(curScore);
      var selectionEnd = new Cursor(curScore);
      cursor.goToSelectionStart();
      selectionEnd.goToSelectionEnd();

      var startStaff = cursor.staff;
      var endStaff = selectionEnd.staff;

      for (var staff = startStaff; staff<endStaff; ++staff) {
          cursor.goToSelectionStart();
          for (var v=0; v<4; v++) {
              cursor.goToSelectionStart();
              cursor.voice = v;
              cursor.staff = staff;

              while (cursor.tick() < selectionEnd.tick()) {
                    if (cursor.isChord()) {
                       var chord = cursor.chord();
                       if (chord.notes>1) {
                           for (var i = 0; i<chord.notes; i++) {
                              var note = chord.note(i);
                              chord.removeNote(i);
                           }
                        }
                    }
              cursor.next();
              }
        }
      }
}
var mscorePlugin = {
      majorVersion: 0,
      minorVersion: 1,
      menu: 'Plugins.Zap Chords',
      init: init,
      run:  run
      };

mscorePlugin;

<|endoftext|>


<commit_before>'use strict'

import { StyleSheet } from 'react-native'
import { Fonts, Colors, Metrics } from '../../Themes/'

export default StyleSheet.create({
  button: {
    height: 45,
    borderRadius: 5,
    marginHorizontal: Metrics.section,
    marginVertical: Metrics.baseMargin,
    backgroundColor: Colors.fire,
    justifyContent: 'center'
  },
  buttonText: {
    color: Colors.snow,
    textAlign: 'center',
    fontWeight: 'bold',
    fontSize: Fonts.size.medium,
    paddingVertical: Metrics.baseMargin
  }
})
<commit_msg>Fix text vert margin on RoundedButton<commit_after>'use strict'

import { StyleSheet } from 'react-native'
import { Fonts, Colors, Metrics } from '../../Themes/'

export default StyleSheet.create({
  button: {
    height: 45,
    borderRadius: 5,
    marginHorizontal: Metrics.section,
    marginVertical: Metrics.baseMargin,
    backgroundColor: Colors.fire,
    justifyContent: 'center'
  },
  buttonText: {
    color: Colors.snow,
    textAlign: 'center',
    fontWeight: 'bold',
    fontSize: Fonts.size.medium,
    marginVertical: Metrics.baseMargin
  }
})
<|endoftext|>


<commit_before>/*
 *   Copyright 2015 OSBI
 *
 *   Created by Andreas Verleysen
 */

/**
 * Changes the locale of the cube
 */
var ChangeLocale = Backbone.View.extend({

    initialize: function (args) {
        this.visible = false;

        this.workspace = args.workspace;

        // Create a unique ID for use as the CSS selector
        this.id = _.uniqueId("changeLocale_");
        $(this.el).attr({ id: this.id });

        // Bind table rendering to query result event
        _.bindAll(this, "render", "show", "handleClick", "processDatasourcesWithoutAddingNewTab", "toggleLocaleScreen", "setUserFeedback");

        this.datasources = new Connections({}, { dialog: this });

        // Add change locale button to saiku toolbar
        this.add_button();
        this.workspace.toolbar.changeLocale = this.show;

        this.localeOptionsScreenTemplate = _.template("" +
            "
  " +
            "
" +
            "<%_.each(localeMap, function(localeCode, language){ %>" +
            "
         <button class='button' id='<%=localeCode%>' > <%=language%> </button>
 " +
            "<%})%>" +
            "
" +
            "
 " +
            " Choose your language " +
            "");

        // Create locale screen
        this.localeOptionsScreen = $(this.localeOptionsScreenTemplate({localeMap: Settings.MONDRIAN_LOCALES}));

        // attach event handler
        this.localeOptionsScreen.find('button').click(this.handleClick);

        //function for menu
        $("#nav ul ").css({display: "none"}); // Opera Fix
        $("#nav li").hover(function () {
            $(this).find('ul:first').css({visibility: "visible", display: "none"}).show(400);
        }, function () {
            $(this).find('ul:first').css({visibility: "hidden"});
        });

        // Append chart to workspace
        $(this.workspace.el).find('.workspace_results')
            .prepend($(this.el).hide())
            .prepend(this.localeOptionsScreen.hide());

    },

    add_button: function () {
        var $chart_button =
            $('')
                .css({  'background-image': "url('js/saiku/plugins/ChangeLocale/images/change_locale.png')",
                    'background-repeat': 'no-repeat',
                    'background-position': '7px 7px'
                });

        var $chart_li = $('

').append($chart_button);
        $(this.workspace.toolbar.el).find("ul").append($chart_li);
    },

    show: function (event, ui) {
        this.toggleWorkspaceWithLocaleScreen();
//        if ($(event.target).hasClass('on')) {
//            this.render();
//        } else {
//            this.workspace.table.render({ data: this.workspace.query.result.lastresult() });
//        }
    },

    toggleWorkspaceWithLocaleScreen: function () {
        this.toggleWorkSpace();
        this.toggleLocaleScreen();
    },

    toggleWorkSpace: function () {
        $(this.workspace.table.el).toggle();
        $(this.el).toggle();
    },

    toggleLocaleScreen: function () {
        if (this.visible) {
            this.setUserFeedback("Choose language");
            $(this.workspace.el).find('#languageOptions').addClass('hide');
            $(this.workspace.el).find('#feedback').addClass('hide');
            this.workspace.toolbar.run_query();
        }
        else {
            $(this.workspace.el).find('#languageOptions').removeClass('hide').show();
            $(this.workspace.el).find('#feedback').removeClass('hide').show();
        }
        $("#changeLocaleBtn").toggleClass('on');
        this.visible = !this.visible;
    },

    handleClick: function (event) {
        // Keep a reference to the main plugin object.
        var this_p = this;
        this_p.setUserFeedback("Changing locale...");
        // get selected locale
        var newLocale = $(event.target).attr('id');

        // get current selected connection name (without URL data)
        var selectedCube = $(".cubes option:selected").val();
        var selectedConnectionName = selectedCube.substring(0, selectedCube.indexOf("/"));

        //send connection name to back-end for update
        this_p.setUserFeedback("Persisting locale...");
        this_p.persistLocaleOfDataSource(selectedConnectionName, newLocale);
        this_p.setUserFeedback("Refreshing data source with new locale...");
        this_p.refreshDatasources();

        return false;
    },

    persistLocaleOfDataSource: function (selectedDataSourceName, newLocale) {
        putUrl = Settings.REST_URL + "admin/datasources/" + selectedDataSourceName + "/locale";

        var xhr = new XMLHttpRequest();
        xhr.open('PUT', putUrl, false);
        xhr.setRequestHeader('Content-Type', 'application/json');
        xhr.send(newLocale);
    },

    refreshDatasources: function () {
        // keep reference to this plugin
        var this_plugin = this;
        if (typeof localStorage !== "undefined" && localStorage) {
            localStorage.clear();
        }

        Saiku.session.sessionworkspace.clear();

        if (typeof localStorage !== "undefined" && localStorage) {
            localStorage.setItem('saiku-version', Settings.VERSION);
        }

        Saiku.session.sessionworkspace.fetch({success: this_plugin.processDatasourcesWithoutAddingNewTab}, {});
    },

    processDatasourcesWithoutAddingNewTab: function (model, response) {
        // Save session in localStorage for other tabs to use
        if (typeof localStorage !== "undefined" && localStorage && localStorage.getItem('session') === null) {
            localStorage.setItem('session', JSON.stringify(response));

            // Set expiration on localStorage to one day in the future
            var expires = (new Date()).getTime() + Settings.LOCALSTORAGE_EXPIRATION;
            if (typeof localStorage !== "undefined" && localStorage) {
                localStorage.setItem('expiration', expires);
            }
        }

        // Generate cube navigation for reuse
        Saiku.session.sessionworkspace.cube_navigation = _.template($("#template-cubes").html())({
            connections: response
        });

        // Create cube objects
        Saiku.session.sessionworkspace.cube = {};
        Saiku.session.sessionworkspace.connections = response;
        _.delay(Saiku.session.sessionworkspace.prefetch_dimensions, 20);

        this.show();
    },

    setUserFeedback: function (msg) {
        $("#feedback").html(msg);
    }
});

var DataSource = Backbone.Model.extend({
//    url: "admin/datasources",
    urlRoot: "admin/datasources",
    refresh: function () {
        $.ajax({
            type: 'GET',
            url: Settings.REST_URL + "admin" + "/datasources/" + this.get("connectionname") + "/refresh"
        });
    }
});

/**
 * Start Plugin
 */
Saiku.events.bind('session:new', function (session) {

    function new_workspace(args) {
        if (typeof args.workspace.changeLocale == "undefined") {
            args.workspace.changeLocale = new ChangeLocale({ workspace: args.workspace });
        }
    };

    function clear_workspace(args) {
        if (typeof args.workspace.changeLocale != "undefined") {
            $(args.workspace.changeLocale.localeOptionsScreen).hide();
            $(args.workspace.changeLocale.el).parents().find('.workspace_results table').show();
            $(args.workspace.changeLocale.el).hide();
        }
    };

    if (Settings.PLUGINS.indexOf("ChangeLocale") != -1) {
        // Attach to existing tabs
        for (var i = 0; i < Saiku.tabs._tabs.length; i++) {
            var tab = Saiku.tabs._tabs[i];
            new_workspace({
                workspace: tab.content
            });
        }
        ;

        // Attach to future tabs
        Saiku.session.bind("workspace:new", new_workspace);
        Saiku.session.bind("workspace:clear", clear_workspace);
    }
});
<commit_msg>ChangeLocale: pretty buttons<commit_after>/*
 *   Copyright 2015 OSBI
 *
 *   Created by Andreas Verleysen
 */

/**
 * Changes the locale of the cube
 */
var ChangeLocale = Backbone.View.extend({

    initialize: function (args) {
        this.visible = false;

        this.workspace = args.workspace;

        // Create a unique ID for use as the CSS selector
        this.id = _.uniqueId("changeLocale_");
        $(this.el).attr({ id: this.id });

        // Bind table rendering to query result event
        _.bindAll(this, "render", "show", "handleClick", "processDatasourcesWithoutAddingNewTab", "toggleLocaleScreen", "setUserFeedback");

        this.datasources = new Connections({}, { dialog: this });

        // Add change locale button to saiku toolbar
        this.add_button();
        this.workspace.toolbar.changeLocale = this.show;

        this.localeOptionsScreenTemplate = _.template("" +
            "

 Choose your language

" +
            "
  " +
            "
" +
            "<%_.each(localeMap, function(localeCode, language){ %>" +
            "
         <button class='form_button' style='padding-bottom: 18px;' id='<%=localeCode%>' > <%=language%> </button>
 " +
            "<%})%>" +
            "
" +
            "
 " +
            "");

        // Create locale screen
        this.localeOptionsScreen = $(this.localeOptionsScreenTemplate({localeMap: Settings.MONDRIAN_LOCALES}));

        // attach event handler
        this.localeOptionsScreen.find('button').click(this.handleClick);

        //function for menu
        $("#nav ul ").css({display: "none"}); // Opera Fix
        $("#nav li").hover(function () {
            $(this).find('ul:first').css({visibility: "visible", display: "none"}).show(400);
        }, function () {
            $(this).find('ul:first').css({visibility: "hidden"});
        });

        // Append chart to workspace
        $(this.workspace.el).find('.workspace_results')
            .prepend($(this.el).hide())
            .prepend(this.localeOptionsScreen.hide());

    },

    add_button: function () {
        var $chart_button =
            $('')
                .css({  'background-image': "url('js/saiku/plugins/ChangeLocale/images/change_locale.png')",
                    'background-repeat': 'no-repeat',
                    'background-position': '7px 7px'
                });

        var $chart_li = $('

').append($chart_button);
        $(this.workspace.toolbar.el).find("ul").append($chart_li);
    },

    show: function (event, ui) {
        this.toggleWorkspaceWithLocaleScreen();
//        if ($(event.target).hasClass('on')) {
//            this.render();
//        } else {
//            this.workspace.table.render({ data: this.workspace.query.result.lastresult() });
//        }
    },

    toggleWorkspaceWithLocaleScreen: function () {
        this.toggleWorkSpace();
        this.toggleLocaleScreen();
    },

    toggleWorkSpace: function () {
        $(this.workspace.table.el).toggle();
        $(this.el).toggle();
    },

    toggleLocaleScreen: function () {
        if (this.visible) {
            this.setUserFeedback("Choose language");
            $(this.workspace.el).find('#languageOptions').addClass('hide');
            $(this.workspace.el).find('#feedback').addClass('hide');
            this.workspace.toolbar.run_query();
        }
        else {
            $(this.workspace.el).find('#languageOptions').removeClass('hide').show();
            $(this.workspace.el).find('#feedback').removeClass('hide').show();
        }
        $("#changeLocaleBtn").toggleClass('on');
        this.visible = !this.visible;
    },

    handleClick: function (event) {
        // Keep a reference to the main plugin object.
        var this_p = this;
        this_p.setUserFeedback("Changing locale...");
        // get selected locale
        var newLocale = $(event.target).attr('id');

        // get current selected connection name (without URL data)
        var selectedCube = $(".cubes option:selected").val();
        var selectedConnectionName = selectedCube.substring(0, selectedCube.indexOf("/"));

        //send connection name to back-end for update
        this_p.setUserFeedback("Persisting locale...");
        this_p.persistLocaleOfDataSource(selectedConnectionName, newLocale);
        this_p.setUserFeedback("Refreshing data source with new locale...");
        this_p.refreshDatasources();

        return false;
    },

    persistLocaleOfDataSource: function (selectedDataSourceName, newLocale) {
        var putUrl = Settings.REST_URL + "admin/datasources/" + selectedDataSourceName + "/locale";

        var xhr = new XMLHttpRequest();
        xhr.open('PUT', putUrl, false);
        xhr.setRequestHeader('Content-Type', 'application/json');
        xhr.send(newLocale);
    },

    refreshDatasources: function () {
        // keep reference to this plugin
        var this_plugin = this;
        if (typeof localStorage !== "undefined" && localStorage) {
            localStorage.clear();
        }

        Saiku.session.sessionworkspace.clear();

        if (typeof localStorage !== "undefined" && localStorage) {
            localStorage.setItem('saiku-version', Settings.VERSION);
        }

        Saiku.session.sessionworkspace.fetch({success: this_plugin.processDatasourcesWithoutAddingNewTab}, {});
    },

    processDatasourcesWithoutAddingNewTab: function (model, response) {
        // Save session in localStorage for other tabs to use
        if (typeof localStorage !== "undefined" && localStorage && localStorage.getItem('session') === null) {
            localStorage.setItem('session', JSON.stringify(response));

            // Set expiration on localStorage to one day in the future
            var expires = (new Date()).getTime() + Settings.LOCALSTORAGE_EXPIRATION;
            if (typeof localStorage !== "undefined" && localStorage) {
                localStorage.setItem('expiration', expires);
            }
        }

        // Generate cube navigation for reuse
        Saiku.session.sessionworkspace.cube_navigation = _.template($("#template-cubes").html())({
            connections: response
        });

        // Create cube objects
        Saiku.session.sessionworkspace.cube = {};
        Saiku.session.sessionworkspace.connections = response;
        _.delay(Saiku.session.sessionworkspace.prefetch_dimensions, 20);

        this.show();
    },

    setUserFeedback: function (msg) {
        $("#feedback").html("
" + msg + "
");
    }
});

var DataSource = Backbone.Model.extend({
//    url: "admin/datasources",
    urlRoot: "admin/datasources",
    refresh: function () {
        $.ajax({
            type: 'GET',
            url: Settings.REST_URL + "admin" + "/datasources/" + this.get("connectionname") + "/refresh"
        });
    }
});

/**
 * Start Plugin
 */
Saiku.events.bind('session:new', function (session) {

    function new_workspace(args) {
        if (typeof args.workspace.changeLocale == "undefined") {
            args.workspace.changeLocale = new ChangeLocale({ workspace: args.workspace });
        }
    };

    function clear_workspace(args) {
        if (typeof args.workspace.changeLocale != "undefined") {
            $(args.workspace.changeLocale.localeOptionsScreen).hide();
            $(args.workspace.changeLocale.el).parents().find('.workspace_results table').show();
            $(args.workspace.changeLocale.el).hide();
        }
    };

    if (Settings.PLUGINS.indexOf("ChangeLocale") != -1) {
        // Attach to existing tabs
        for (var i = 0; i < Saiku.tabs._tabs.length; i++) {
            var tab = Saiku.tabs._tabs[i];
            new_workspace({
                workspace: tab.content
            });
        }
        ;

        // Attach to future tabs
        Saiku.session.bind("workspace:new", new_workspace);
        Saiku.session.bind("workspace:clear", clear_workspace);
    }
});
<|endoftext|>


<commit_before>import app from '../../admin/app';
import DashboardWidget from './DashboardWidget';
import listItems from '../../common/helpers/listItems';
import ItemList from '../../common/utils/ItemList';
import Dropdown from '../../common/components/Dropdown';
import Button from '../../common/components/Button';
import LoadingModal from './LoadingModal';

export default class StatusWidget extends DashboardWidget {
  className() {
    return 'StatusWidget';
  }

  content() {
    return
{listItems(this.items().toArray())}
;
  }

  items() {
    const items = new ItemList();

    items.add(
      'tools',
      <Dropdown
        label={app.translator.trans('core.admin.dashboard.tools_button')}
        icon="fas fa-cog"
        buttonClassName="Button"
        menuClassName="Dropdown-menu--right"
      >
        <Button onclick={this.handleClearCache.bind(this)}>{app.translator.trans('core.admin.dashboard.clear_cache_button')}</Button>
      </Dropdown>
    );

    items.add('version-flarum', [Flarum,
, app.forum.attribute('version')]);
    items.add('version-php', [PHP,
, app.data.phpVersion]);
    items.add('version-mysql', [MySQL,
, app.data.mysqlVersion]);

    return items;
  }

  handleClearCache(e) {
    app.modal.show(LoadingModal);

    app
      .request({
        method: 'DELETE',
        url: app.forum.attribute('apiUrl') + '/cache',
      })
      .then(() => window.location.reload());
  }
}
<commit_msg>Make StatusWidget tools extensible (#3189)<commit_after>import app from '../../admin/app';
import DashboardWidget from './DashboardWidget';
import listItems from '../../common/helpers/listItems';
import ItemList from '../../common/utils/ItemList';
import Dropdown from '../../common/components/Dropdown';
import Button from '../../common/components/Button';
import LoadingModal from './LoadingModal';

export default class StatusWidget extends DashboardWidget {
  className() {
    return 'StatusWidget';
  }

  content() {
    return
{listItems(this.items().toArray())}
;
  }

  items() {
    const items = new ItemList();

    items.add(
      'tools',
      <Dropdown
        label={app.translator.trans('core.admin.dashboard.tools_button')}
        icon="fas fa-cog"
        buttonClassName="Button"
        menuClassName="Dropdown-menu--right"
      >
        {this.toolsItems().toArray()}
      </Dropdown>
    );

    items.add('version-flarum', [Flarum,
, app.forum.attribute('version')]);
    items.add('version-php', [PHP,
, app.data.phpVersion]);
    items.add('version-mysql', [MySQL,
, app.data.mysqlVersion]);

    return items;
  }

  toolsItems() {
    const items = new ItemList();

    items.add(
      'clearCache',
      <Button onclick={this.handleClearCache.bind(this)}>{app.translator.trans('core.admin.dashboard.clear_cache_button')}</Button>
    );

    return items;
  }

  handleClearCache(e) {
    app.modal.show(LoadingModal);

    app
      .request({
        method: 'DELETE',
        url: app.forum.attribute('apiUrl') + '/cache',
      })
      .then(() => window.location.reload());
  }
}
<|endoftext|>


<commit_before>import BaseVw from '../baseVw';
import loadTemplate from '../../utils/loadTemplate';

export default class extends BaseVw {
  constructor(options = {}) {
    const opts = {
      initialState: {
        hidden: true,
        showSpinner: true,
        loaded: 0,
        total: 0,
        mode: 'loaded',
      },
      ...options,
      ...(options && options.initialState || {}),
    };

    super(opts);
    this.options = opts;
  }

  className() {
    return 'moderatorStatus';
  }

  render() {
    super.render();

    loadTemplate('components/moderatorsStatus.html', (t) => {
      this.$el.html(t({
        ...this.getState(),
      }));
    });

    return this;
  }
}
<commit_msg>fix initialstate<commit_after>import BaseVw from '../baseVw';
import loadTemplate from '../../utils/loadTemplate';

export default class extends BaseVw {
  constructor(options = {}) {
    const opts = {
      initialState: {
        hidden: true,
        showSpinner: true,
        loaded: 0,
        total: 0,
        mode: 'loaded',
        ...(options && options.initialState || {}),
      },
      ...options,
     };

    super(opts);
    this.options = opts;
  }

  className() {
    return 'moderatorStatus';
  }

  render() {
    super.render();

    loadTemplate('components/moderatorsStatus.html', (t) => {
      this.$el.html(t({
        ...this.getState(),
      }));
    });

    return this;
  }
}
<|endoftext|>


<commit_before>var util = require('util')
  , fs = require('fs')
  , spawn = require('./spawn')
  , errors = require('./errors')
  , cwd = process.cwd();

/**
 * Make some curl opts friendlier.
 */

var curl_map = {
    timeout: 'max-time'
  , redirects: 'max-redirs'
  , method: 'request'
  , useragent: 'user-agent'
};

/**
 * Default user-agents.
 */

var user_agents = require('./useragents.js')
  , user_agents_len = user_agents.length;

/**
 * Default request headers.
 */

var default_headers = {
    'Accept': '*/*'
  , 'Accept-Charset': 'ISO-8859-1,utf-8;q=0.7,*;q=0.3'
  , 'Accept-Language': 'en-US,en;q=0.8'
};

/**
 * Make a request with cURL.
 *
 * @param {Object|String} options (optional) - see `man curl`
 * @param {Function} callback (optional)
 * @api public
 */

exports.request = function (options, callback) {
    if (arguments.length === 1) {
        var defaults = options;
        return function (options, callback) {
            if (typeof options === 'function') {
                callback = options;
                options = {};
            } else if (typeof options === 'string') {
                options = { url: options };
            }
            for (var key in defaults) {
                if (typeof options[key] === 'undefined') {
                    options[key] = defaults[key];
                }
            }
            exports.request.call(this, options, callback);
        };
    }

    if (options.retries) {
        var remaining = options.retries;
        delete options.retries;
        return (function curl() {
            exports.request(options, function (err) {
                if (!err || !--remaining) {
                    return callback.apply(this, arguments);
                }
                process.nextTick(curl);
            });
        })();
    }

    if (typeof options === 'string') {
        options = { url: options };
    } else {
        options = exports.copy(options);
    }

    for (var key in curl_map) {
        if (typeof options[key] !== 'undefined') {
            options[curl_map[key]] = options[key];
            delete options[key];
        }
    }

    var curl
      , curl_path = 'curl'
      , args = ['--silent', '--show-error', '--no-buffer']
      , start = new Date
      , err
      , stderr = ''
      , stdoutlen
      , stdout = new Buffer(stdoutlen = 0)
      , encoding
      , complete
      , cleanup
      , postprocess
      , require_str
      , require_not_str
      , scope = {}
      , cmd = 'curl'
      , timeout;

    function finish() {
        if (options.fail && stderr) {
            err = String(stderr).replace(/^curl: \(\d+\) /, ''); // "curl: (22) The requested URL returned error..." => "The requested URL returned error..."
        } else if (err in errors) {
            err = errors[err];
        }
        callback.call(scope, err, stdout, {
            cmd: cmd
          , args: args
          , time: (new Date().getTime() - start.getTime())
        });
        complete = true;
    }

    //Allow for a custom curl path
    if (options.curl_path) {
        curl_path = options.curl_path;
        delete options.curl_path;
    }

    //Follow location by default
    if ('max-redirs' in options) {
        options.location = !!options['max-redirs'];
    } else {
        options.location = true;
        options['max-redirs'] = 3;
    }

    //Add an additional setTimeout for max-time
    if (options['max-time']) {
        timeout = setTimeout(function () {
            if (complete) return;
            stderr = 'timeout', stdout = null;
            finish();
            if (curl && curl.kill) curl.kill('SIGKILL');
        }, 1000 * options['max-time']);
    }

    //Default encoding is utf8. Set encoding = null to get a buffer
    if (!options.encoding && options.encoding !== null) {
        options.encoding = 'utf8';
    }
    encoding = options.encoding;
    if (encoding === 'ascii') {
        options['use-ascii'] = true;
    }
    delete options.encoding;

    //Parse POST data
    if (options.data && typeof options.data === 'object') {
        var data = [];
        for (var key in options.data) {
            data.push(encodeURIComponent(key) + '=' + encodeURIComponent(options.data[key]));
        }
        options.data = data.join('&');
    }

    //Check for the occurrence of a string and fail if not found
    if (options.require) {
        require_str = options.require;
        if (!Array.isArray(require_str)) {
            require_str = [require_str];
        }
        delete options.require;
    }

    //Check for the occurrence of a string and fail if found
    if (options.require_not) {
        require_not_str = options.require_not;
        if (!Array.isArray(require_not_str)) {
            require_not_str = [require_not_str];
        }
        delete options.require_not;
    }

    //Call the callback in a custom scope
    if (options.scope) {
        scope = options.scope;
        delete options.scope;
    }

    //Apply a post-processing function?
    if (options.process) {
        postprocess = options.process;
        delete options.process;
    }

    //Setup default headers
    var key, headers = {};
    for (key in default_headers) {
        headers[key] = default_headers[key];
    }
    if (options.headers) {
        var normalised_key;
        for (key in options.headers) {
            normalised_key = key.replace(/[_-]/g, ' ').split(' ').map(function (str) {
                if (str.length) {
                    str = str[0].toUpperCase() + str.substr(1);
                }
                return str;
            }).join('-');
            headers[normalised_key] = options.headers[key];
        }
        delete options.headers;
    }
    options.header = options.header || [];
    for (key in headers) {
        options.header.push(key + ': ' + headers[key]);
    }

    //Select a random user agent if one wasn't provided
    if (!headers['User-Agent'] && !options['user-agent']) {
        options['user-agent'] = user_agents[Math.random() * user_agents_len | 0];
    }

    //Prepare curl args
    var key, values;
    for (key in options) {
        if (key === 'pretend') {
            continue;
        }
        values = Array.isArray(options[key]) ? options[key] : [options[key]];
        values.forEach(function (value) {
            args.push('--' + key);
            if (true !== value) {
                args.push(value);
            }
        });
    }

    if (options.file) {
        cmd = 'cat';
        args = [options.file];
    }

    //Simulate the spawn?
    if (options.pretend) {
        return finish();
    }

    //Spawn the process
    var child = spawn(cmd, args, { cwd: options.cwd || cwd }, function (curl) {

        //Collect stdout
        if(curl && curl.stdout){
            curl.stdout.on('data', function (data) {
                if (complete) return;
                var len = data.length, prev = stdout;
                stdout = new Buffer(len + stdoutlen);
                prev.copy(stdout, 0, 0, stdoutlen);
                data.copy(stdout, stdoutlen, 0, len);
                stdoutlen += len;
            });
        }

        //Pipe stderr to the current process?
        if (options.stderr) {
            if (options.stderr === true) {
                curl.stderr.pipe(process.stderr);
                delete options.stderr
            }
        }

        curl.stderr.on('data', function (data) {
          if (complete) return;
          stderr += data;
        });

        //Handle curl exit
        curl.on('close', function (code) {
            try {
                err = code;
                if (complete) return;
                if (encoding) {
                    stdout = stdout.toString(encoding);
                }
                if (postprocess && stdout) {
                    stdout = postprocess(stdout);
                }
                if (require_str) {
                    var valid = false;
                    if (!encoding) {
                        stdout = stdout.toString();
                    }
                    var str;
                    for (var i = 0, l = require_str.length; i < l; i++) {
                        str = require_str[i];
                        if ((util.isRegExp(str) && str.test(stdout)) || stdout.indexOf(str) !== -1) {
                            valid = true;
                            break;
                        }
                    }
                    if (!valid) {
                        err = 'response does not contain required string: ' + str;
                        stdout = null
                    } else if (!encoding) {
                        stdout = new Buffer(stdout);
                    }
                }
                if (require_not_str) {
                    var valid = true;
                    if (!encoding) {
                        stdout = stdout.toString();
                    }
                    var str;
                    for (var i = 0, l = require_not_str.length; i < l; i++) {
                        str = require_not_str[i];
                        if ((util.isRegExp(str) && str.test(stdout)) || stdout.indexOf(str) !== -1) {
                            valid = false;
                            break;
                        }
                    }
                    if (!valid) {
                        err = 'response contains bad string: ' + str;
                        stdout = null
                    } else if (!encoding) {
                        stdout = new Buffer(stdout);
                    }
                }
            } catch (e) {
                err = typeof e === 'object' ? e.message || '' : e;
            }
            finish();
            if (timeout) clearTimeout(timeout);
        });
    });
};

/**
 * Expose a helper for scraping urls from a page.
 */

var urls = /(?:href|src|HREF|SRC)=["']?([^"' >]+)/g;

exports.urls = function (data, regex) {
    var match, matches = [];
    while (match = urls.exec(data)) {
        if (regex && !regex.test(match[1])) {
            continue;
        }
        matches.push(match[1].replace(/[\r\n\t\s]/g, ''));
    }
    return matches;
};

/**
 * A helper for handling async concurrency.
 */

exports.concurrent = function (input, concurrency, fn) {
    if (arguments.length === 3) {
        var len = input.length, pos = 0, remaining = concurrency;
        for (var i = 0; i < concurrency; i++) {
            (function exec() {
                if (pos >= len) {
                    if (!--remaining) {
                        fn(null, function () {});
                    }
                } else {
                    fn(input[pos++], function () {
                        process.nextTick(exec);
                    });
                }
            })();
        }
    } else {
        fn = concurrency;
        concurrency = input;
        for (var i = 0; i < concurrency; i++) {
            (function exec() {
                fn(function () {
                    process.nextTick(exec);
                });
            })();
        }
    }
};

/**
 * A helper for copying an object.
 */

exports.copy = function (obj) {
    var copy = {};
    for (var i in obj) {
        if (Array.isArray(obj[i])) {
            copy[i] = obj[i].map(function (item) {
                return item;
            });
        } else if (typeof obj[i] === 'object') {
            copy[i] = obj[i] ? exports.copy(obj[i]) : null;
        } else {
            copy[i] = obj[i];
        }
    }
    return copy;
};

<commit_msg>updated<commit_after>var util = require('util')
  , fs = require('fs')
  , spawn = require('./spawn')
  , errors = require('./errors')
  , cwd = process.cwd();

/**
 * Make some curl opts friendlier.
 */

var curl_map = {
    timeout: 'max-time'
  , redirects: 'max-redirs'
  , method: 'request'
  , useragent: 'user-agent'
};

/**
 * Default user-agents.
 */

var user_agents = require('./useragents.js')
  , user_agents_len = user_agents.length;

/**
 * Default request headers.
 */

var default_headers = {
    'Accept': '*/*'
  , 'Accept-Charset': 'ISO-8859-1,utf-8;q=0.7,*;q=0.3'
  , 'Accept-Language': 'en-US,en;q=0.8'
};

/**
 * Make a request with cURL.
 *
 * @param {Object|String} options (optional) - see `man curl`
 * @param {Function} callback (optional)
 * @api public
 */

exports.request = function (options, callback) {
    if (arguments.length === 1) {
        var defaults = options;
        return function (options, callback) {
            if (typeof options === 'function') {
                callback = options;
                options = {};
            } else if (typeof options === 'string') {
                options = { url: options };
            }
            for (var key in defaults) {
                if (typeof options[key] === 'undefined') {
                    options[key] = defaults[key];
                }
            }
            exports.request.call(this, options, callback);
        };
    }

    if (options.retries) {
        var remaining = options.retries;
        delete options.retries;
        return (function curl() {
            exports.request(options, function (err) {
                if (!err || !--remaining) {
                    return callback.apply(this, arguments);
                }
                process.nextTick(curl);
            });
        })();
    }

    if (typeof options === 'string') {
        options = { url: options };
    } else {
        options = exports.copy(options);
    }

    for (var key in curl_map) {
        if (typeof options[key] !== 'undefined') {
            options[curl_map[key]] = options[key];
            delete options[key];
        }
    }

    var curl
      , curl_path = 'curl'
      , args = ['--silent', '--show-error', '--no-buffer']
      , start = new Date
      , err
      , stderr = ''
      , stdoutlen
      , stdout = new Buffer(stdoutlen = 0)
      , encoding
      , complete
      , cleanup
      , postprocess
      , require_str
      , require_not_str
      , scope = {}
      , cmd = 'curl'
      , timeout;

    function finish() {
        if (options.fail && stderr) {
            err = String(stderr).replace(/^curl: \(\d+\) /, ''); // "curl: (22) The requested URL returned error..." => "The requested URL returned error..."
        } else if (err in errors) {
            err = errors[err];
        }
        callback.call(scope, err, stdout, {
            cmd: cmd
          , args: args
          , time: (new Date().getTime() - start.getTime())
        });
        complete = true;
    }

    //Allow for a custom curl path
    if (options.curl_path) {
        curl_path = options.curl_path;
        delete options.curl_path;
    }

    //Follow location by default
    if ('max-redirs' in options) {
        options.location = !!options['max-redirs'];
    } else {
        options.location = true;
        options['max-redirs'] = 3;
    }

    //Add an additional setTimeout for max-time
    if (options['max-time']) {
        timeout = setTimeout(function () {
            if (complete) return;
            stderr = 'timeout', stdout = null;
            finish();
            if (curl && curl.kill) curl.kill('SIGKILL');
        }, 1000 * options['max-time']);
    }

    //Default encoding is utf8. Set encoding = null to get a buffer
    if (!options.encoding && options.encoding !== null) {
        options.encoding = 'utf8';
    }
    encoding = options.encoding;
    if (encoding === 'ascii') {
        options['use-ascii'] = true;
    }
    delete options.encoding;

    //Parse POST data
    if (options.data && typeof options.data === 'object') {
        var data = [];
        for (var key in options.data) {
            data.push(encodeURIComponent(key) + '=' + encodeURIComponent(options.data[key]));
        }
        options.data = data.join('&');
    }

    //Check for the occurrence of a string and fail if not found
    if (options.require) {
        require_str = options.require;
        if (!Array.isArray(require_str)) {
            require_str = [require_str];
        }
        delete options.require;
    }

    //Check for the occurrence of a string and fail if found
    if (options.require_not) {
        require_not_str = options.require_not;
        if (!Array.isArray(require_not_str)) {
            require_not_str = [require_not_str];
        }
        delete options.require_not;
    }

    //Call the callback in a custom scope
    if (options.scope) {
        scope = options.scope;
        delete options.scope;
    }

    //Apply a post-processing function?
    if (options.process) {
        postprocess = options.process;
        delete options.process;
    }

    //Setup default headers
    var key, headers = {};
    for (key in default_headers) {
        headers[key] = default_headers[key];
    }
    if (options.headers) {
        var normalised_key;
        for (key in options.headers) {
            normalised_key = key.replace(/[_-]/g, ' ').split(' ').map(function (str) {
                if (str.length) {
                    str = str[0].toUpperCase() + str.substr(1);
                }
                return str;
            }).join('-');
            headers[normalised_key] = options.headers[key];
        }
        delete options.headers;
    }
    options.header = options.header || [];
    for (key in headers) {
        options.header.push(key + ': ' + headers[key]);
    }

    //Select a random user agent if one wasn't provided
    if (!headers['User-Agent'] && !options['user-agent']) {
        options['user-agent'] = user_agents[Math.random() * user_agents_len | 0];
    }

    //Prepare curl args
    var key, values;
    for (key in options) {
        if (key === 'pretend') {
            continue;
        }
        values = Array.isArray(options[key]) ? options[key] : [options[key]];
        values.forEach(function (value) {
            args.push('--' + key);
            if (true !== value) {
                args.push(value);
            }
        });
    }

    if (options.file) {
        cmd = 'cat';
        args = [options.file];
    }

    //Simulate the spawn?
    if (options.pretend) {
        return finish();
    }

    //Spawn the process
    var child = spawn(cmd, args, { cwd: options.cwd || cwd }, function (curl) {

        //Collect stdout
        if(curl && curl.stdout){
            curl.stdout.on('data', function (data) {
                if (complete) return;
                var len = data.length, prev = stdout;
                stdout = new Buffer(len + stdoutlen);
                prev.copy(stdout, 0, 0, stdoutlen);
                data.copy(stdout, stdoutlen, 0, len);
                stdoutlen += len;
            });
        }

        //Pipe stderr to the current process?
        if (options.stderr) {
            if (options.stderr === true) {
                curl.stderr.pipe(process.stderr);
                delete options.stderr
            }
        }
        if(curl && curl.stderr){
            curl.stderr.on('data', function (data) {
               if (complete) return;
                stderr += data;
            });
        }
        curl.stderr.on('data', function (data) {
          if (complete) return;
          stderr += data;
        });

        //Handle curl exit
        curl.on('close', function (code) {
            try {
                err = code;
                if (complete) return;
                if (encoding) {
                    stdout = stdout.toString(encoding);
                }
                if (postprocess && stdout) {
                    stdout = postprocess(stdout);
                }
                if (require_str) {
                    var valid = false;
                    if (!encoding) {
                        stdout = stdout.toString();
                    }
                    var str;
                    for (var i = 0, l = require_str.length; i < l; i++) {
                        str = require_str[i];
                        if ((util.isRegExp(str) && str.test(stdout)) || stdout.indexOf(str) !== -1) {
                            valid = true;
                            break;
                        }
                    }
                    if (!valid) {
                        err = 'response does not contain required string: ' + str;
                        stdout = null
                    } else if (!encoding) {
                        stdout = new Buffer(stdout);
                    }
                }
                if (require_not_str) {
                    var valid = true;
                    if (!encoding) {
                        stdout = stdout.toString();
                    }
                    var str;
                    for (var i = 0, l = require_not_str.length; i < l; i++) {
                        str = require_not_str[i];
                        if ((util.isRegExp(str) && str.test(stdout)) || stdout.indexOf(str) !== -1) {
                            valid = false;
                            break;
                        }
                    }
                    if (!valid) {
                        err = 'response contains bad string: ' + str;
                        stdout = null
                    } else if (!encoding) {
                        stdout = new Buffer(stdout);
                    }
                }
            } catch (e) {
                err = typeof e === 'object' ? e.message || '' : e;
            }
            finish();
            if (timeout) clearTimeout(timeout);
        });
    });
};

/**
 * Expose a helper for scraping urls from a page.
 */

var urls = /(?:href|src|HREF|SRC)=["']?([^"' >]+)/g;

exports.urls = function (data, regex) {
    var match, matches = [];
    while (match = urls.exec(data)) {
        if (regex && !regex.test(match[1])) {
            continue;
        }
        matches.push(match[1].replace(/[\r\n\t\s]/g, ''));
    }
    return matches;
};

/**
 * A helper for handling async concurrency.
 */

exports.concurrent = function (input, concurrency, fn) {
    if (arguments.length === 3) {
        var len = input.length, pos = 0, remaining = concurrency;
        for (var i = 0; i < concurrency; i++) {
            (function exec() {
                if (pos >= len) {
                    if (!--remaining) {
                        fn(null, function () {});
                    }
                } else {
                    fn(input[pos++], function () {
                        process.nextTick(exec);
                    });
                }
            })();
        }
    } else {
        fn = concurrency;
        concurrency = input;
        for (var i = 0; i < concurrency; i++) {
            (function exec() {
                fn(function () {
                    process.nextTick(exec);
                });
            })();
        }
    }
};

/**
 * A helper for copying an object.
 */

exports.copy = function (obj) {
    var copy = {};
    for (var i in obj) {
        if (Array.isArray(obj[i])) {
            copy[i] = obj[i].map(function (item) {
                return item;
            });
        } else if (typeof obj[i] === 'object') {
            copy[i] = obj[i] ? exports.copy(obj[i]) : null;
        } else {
            copy[i] = obj[i];
        }
    }
    return copy;
};

<|endoftext|>