<commit_before>/*
 * Copyright 2006 The Kuali Foundation
 *
 * Licensed under the Educational Community License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.opensource.org/licenses/ecl2.php
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
function updateLocationByPostalCode( postalCodeField, callbackFunction ) {
	var postalCode = getElementValue( postalCodeField.name );
	var postalCountryCode = getElementValue( findElPrefix( postalCodeField.name ) + ".organizationCountryCode" );

	if ( postalCode != "" && postalCountryCode != "" ) {
		var dwrReply = {
			callback:callbackFunction,
			errorHandler:function( errorMessage ) {
				setRecipientValue( "document.newMaintainableObject.organizationCityName", wrapError( "postal code not found" ), true );
				clearRecipients( "document.newMaintainableObject.organizationStateCode" );
			}
		};
		PostalCodeService.getByPrimaryId(postalCountryCode, postalCode, dwrReply );
	}
}

function updateLocationByPostalCode_Callback( data ) {
	setRecipientValue( "document.newMaintainableObject.organizationCityName", data.postalCityName );
	setRecipientValue( "document.newMaintainableObject.organizationStateCode", data.postalStateCode );
}

function updateLocationByCountryCode( countryCodeField, callbackFunction ) {
	var postalCountryCode = getElementValue( countryCodeField.name );
	var postalCode = getElementValue( findElPrefix( countryCodeField.name ) + ".organizationZipCode" );

	if ( postalCode != "" && postalCountryCode != "" ) {
		var dwrReply = {
			callback:callbackFunction,
			errorHandler:function( errorMessage ) {
				setRecipientValue( "document.newMaintainableObject.organizationCityName", wrapError( "postal code not found" ), true );
				clearRecipients( "document.newMaintainableObject.organizationStateCode" );
			}
		};
		PostalCodeService.getByPrimaryId(postalCountryCode, postalCode, dwrReply );
	}
}

function updateLocationByCountryCode_Callback( data ) {
	setRecipientValue( "document.newMaintainableObject.organizationCityName", data.postalCityName );
	setRecipientValue( "document.newMaintainableObject.organizationStateCode", data.postalStateCode );
}
<commit_msg>KFSMI-7908 altered javascript method calls to match PostalCodeService and renamed PostalCode fields.<commit_after>/*
 * Copyright 2006 The Kuali Foundation
 *
 * Licensed under the Educational Community License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.opensource.org/licenses/ecl2.php
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
function updateLocationByPostalCode( postalCodeField, callbackFunction ) {
	var postalCode = getElementValue( postalCodeField.name );
	var postalCountryCode = getElementValue( findElPrefix( postalCodeField.name ) + ".organizationCountryCode" );

	if ( postalCode != "" && postalCountryCode != "" ) {
		var dwrReply = {
			callback:callbackFunction,
			errorHandler:function( errorMessage ) {
				setRecipientValue( "document.newMaintainableObject.organizationCityName", wrapError( "postal code not found"), true );
				clearRecipients( "document.newMaintainableObject.organizationStateCode" );
			}
		};
		PostalCodeService.getPostalCode(postalCountryCode, postalCode, dwrReply );
	}
}

function updateLocationByPostalCode_Callback( data ) {
	setRecipientValue( "document.newMaintainableObject.organizationCityName", data.cityName );
	setRecipientValue( "document.newMaintainableObject.organizationStateCode", data.stateCode );
}

function updateLocationByCountryCode( countryCodeField, callbackFunction ) {
	var postalCountryCode = getElementValue( countryCodeField.name );
	var postalCode = getElementValue( findElPrefix( countryCodeField.name ) + ".organizationZipCode" );

	if ( postalCode != "" && postalCountryCode != "" ) {
		var dwrReply = {
			callback:callbackFunction,
			errorHandler:function( errorMessage ) {
				setRecipientValue( "document.newMaintainableObject.organizationCityName", wrapError( "postal code not found"), true );
				clearRecipients( "document.newMaintainableObject.organizationStateCode" );
			}
		};
		PostalCodeService.getPostalCode(postalCountryCode, postalCode, dwrReply );
	}
}

function updateLocationByCountryCode_Callback( data ) {
	setRecipientValue( "document.newMaintainableObject.organizationCityName", data.cityName );
	setRecipientValue( "document.newMaintainableObject.organizationStateCode", data.stateCode );
}
<|endoftext|>


<commit_before>/**
 * Copyright reelyActive 2016
 * We believe in an open Internet of Things
 */

DEFAULT_BUBBLE_SIZE = '240px';
BUBBLE_TEMPLATE_URL = '/bubble.html';
TYPE_PERSON = 'Person';
TYPE_PRODUCT = 'Product';
TYPE_PLACE = 'Place';
DEFAULT_IMAGE = {};
DEFAULT_IMAGE[TYPE_PERSON] = 'images/default-person.png';
DEFAULT_IMAGE[TYPE_PRODUCT] = 'images/default-product.png';
DEFAULT_IMAGE[TYPE_PLACE] = 'images/default-place.png';

angular.module('reelyactive.cuttlefish', [])

  .directive('bubble', function() {

    function link(scope, element, attrs) {

      function update() {
        scope.toggle = 0;
        scope.types = [];
        scope.size = scope.size || DEFAULT_BUBBLE_SIZE;

        var graph = scope.json["@graph"];
        for(var cItem = 0; cItem < graph.length; cItem++) {
          switch(graph[cItem]["@type"]) {
            case 'schema:Person':
              scope.person = formatItem(graph[cItem], TYPE_PERSON);
              scope.types.push(TYPE_PERSON);
              break;
            case 'schema:Product':
              scope.product = formatItem(graph[cItem], TYPE_PRODUCT);
              scope.types.push(TYPE_PRODUCT);
              break;
            case 'schema:Place':
              scope.place = formatItem(graph[cItem], TYPE_PLACE);
              scope.types.push(TYPE_PLACE);
              break;
          }
          scope.itemID = graph[cItem]["@id"];
        }
        scope.current = scope.types[0];
      }

      function formatItem(item, type) {
        if(!item.hasOwnProperty("schema:image")) {
          item["schema:image"] = DEFAULT_IMAGE[type];
        }
        return item;
      }

      scope.$watch(attrs.json, function(json) {
        //scope.json = json;
        update();
      });
    }

    return {
      restrict: "E",
      scope: {
        json: "=",
        size: "@"
      },
      link: link,
      templateUrl: BUBBLE_TEMPLATE_URL
    }
  });
<commit_msg>Added leading slash to all paths<commit_after>/**
 * Copyright reelyActive 2016
 * We believe in an open Internet of Things
 */

DEFAULT_BUBBLE_SIZE = '240px';
BUBBLE_TEMPLATE_URL = '/bubble.html'; // May or may not need a leading slash!
TYPE_PERSON = 'Person';
TYPE_PRODUCT = 'Product';
TYPE_PLACE = 'Place';
DEFAULT_IMAGE = {};
DEFAULT_IMAGE[TYPE_PERSON] = '/images/default-person.png';
DEFAULT_IMAGE[TYPE_PRODUCT] = '/images/default-product.png';
DEFAULT_IMAGE[TYPE_PLACE] = '/images/default-place.png';
DEFAULT_IMAGE_UNSUPPORTED = '/images/default-unsupported.png';
UNSUPPORTED_STORY_JSON = {
  "schema:name": "Unsupported Story",
  "schema:image": DEFAULT_IMAGE_UNSUPPORTED
};

angular.module('reelyactive.cuttlefish', [])

  .directive('bubble', function() {

    function link(scope, element, attrs) {

      function update() {
        scope.toggle = 0;
        scope.types = [];
        scope.size = scope.size || DEFAULT_BUBBLE_SIZE;

        if(scope.json && scope.json.hasOwnProperty("@graph")) {
          var graph = scope.json["@graph"];
          for(var cItem = 0; cItem < graph.length; cItem++) {
            switch(graph[cItem]["@type"]) {
              case 'schema:Person':
                scope.person = formatItem(graph[cItem], TYPE_PERSON);
                scope.types.push(TYPE_PERSON);
                break;
              case 'schema:Product':
                scope.product = formatItem(graph[cItem], TYPE_PRODUCT);
                scope.types.push(TYPE_PRODUCT);
                break;
              case 'schema:Place':
                scope.place = formatItem(graph[cItem], TYPE_PLACE);
                scope.types.push(TYPE_PLACE);
                break;
            }
            scope.itemID = graph[cItem]["@id"];
          }
        }
        else {
          scope.product = UNSUPPORTED_STORY_JSON;
          scope.types.push(TYPE_PRODUCT);
        }
        scope.current = scope.types[0];
      }

      function formatItem(item, type) {
        if(!item.hasOwnProperty("schema:image")) {
          item["schema:image"] = DEFAULT_IMAGE[type];
        }
        return item;
      }

      scope.$watch(attrs.json, function(json) {
        //scope.json = json;
        update();
      });
    }

    return {
      restrict: "E",
      scope: {
        json: "=",
        size: "@"
      },
      link: link,
      templateUrl: BUBBLE_TEMPLATE_URL
    }
  });
<|endoftext|>


<commit_before>var state = {
  view: 'welcome',
  url: 'http://siri.cbrp3.c-base.org/deaddrop.json',
  progress: {
    message: 'Publishing on IPFS...',
    percent: 100,
    qrcode: null
  },
  timer: null,
  lastShown: null,
  lastMessageShown: null
};

var drawQr = function (size, element, address) {
  element.innerHTML = '';
  var qrcode = new QRCode(element.id, {
    width: size,
    height: size
  });
  qrcode.makeCode(address);
};

var renderQr = function () {
  var size = window.innerHeight * 0.5;
  var qrcodeEl = document.getElementById('qrcode')
  drawQr(size, qrcodeEl, state.progress.qrcode);
  qrcodeEl.style.width = size + 'px';
  qrcodeEl.style.height = size + 'px';

  qrcodeEl.addEventListener('click', function () {
    window.location.href = state.progress.qrcode;
  });
  var parts = state.progress.qrcode.split('/ipfs/');
  if (parts.length == 1) {
    var qrString = state.progress.qrcode;
  } else {
    var qrString = parts[0] + '/ipfs/
' + parts[1];
  }
  document.getElementById('address').innerHTML = qrString;
};

var renderProgress = function () {
  var statusEl = document.getElementById('status');
  statusEl.value = state.progress.percent;
};

var determineView = function () {
  if (state.progress.qrcode && state.progress.qrcode !== state.lastShown) {
    state.view = 'result';
    return;
  }
  if (state.progress.percent === 100) {
    state.view = 'welcome';
    return;
  }
  state.view = 'progress';
};

var render = function (address) {
  if (state.timer && state.lastShown && state.lastShown !== state.progress.qrcode) {
    window.clearTimeout(state.timer);
    state.timer = null;
  }
  var welcomeEl = document.getElementById('welcome');
  var progressEl = document.getElementById('progress');
  var resultEl = document.getElementById('result');
  switch (state.view) {
    case 'welcome':
      progressEl.style.display = 'none';
      resultEl.style.display = 'none';
      welcomeEl.style.display = 'block';
      break;
    case 'progress':
      state.lastShown = null;
      resultEl.style.display = 'none';
      welcomeEl.style.display = 'none';
      progressEl.style.display = 'block'
      renderProgress();
      break;
    case 'result':
      progressEl.style.display = 'none'
      welcomeEl.style.display = 'none';
      resultEl.style.display = 'block';
      renderQr();
      state.timer = window.setTimeout(function () {
        state.view = 'welcome';
        state.lastShown = state.progress.qrcode;
        state.progress.qrcode = null;
        render();
      }, 240 * 1000);
      break;
  }
  var messageEl = document.getElementById('message');
  if (state.view !== 'welcome' || state.progress.message && state.progress.message.indexOf('Error') !== -1) {
    messageEl.innerHTML = state.progress.message;
    state.progress.lastMessageShown = state.progress.message;
  } else {
    messageEl.innerHTML = '';
  }
  document.body.className = state.view;
};

var address = 'http://siri.cbrp3.c-base.org/deaddrop.json';
if (window.location.search) {
  address = window.location.search.substr(1);
}
state.url = address;

document.addEventListener('DOMContentLoaded', function () {
  render();
  setInterval(function () {
    fetchState();
  }, 1000);
  fetchState();
});
window.addEventListener('resize', function () {
  render();
});

var fetchState = function () {
  var req = new XMLHttpRequest;
  req.open('GET', state.url, true);
  req.onload  = function() {
    if (req.readyState !== 4) {
      return;
    }
    if (req.status === 200) {
      state.progress = JSON.parse(req.responseText);
      determineView();
      render();
    }
  };
  req.send(null);
};
<commit_msg>Add handling for JSON parse errors<commit_after>var state = {
  view: 'welcome',
  url: 'http://siri.cbrp3.c-base.org/deaddrop.json',
  progress: {
    message: 'Publishing on IPFS...',
    percent: 100,
    qrcode: null
  },
  timer: null,
  lastShown: null,
  lastMessageShown: null
};

var drawQr = function (size, element, address) {
  element.innerHTML = '';
  var qrcode = new QRCode(element.id, {
    width: size,
    height: size
  });
  qrcode.makeCode(address);
};

var renderQr = function () {
  var size = window.innerHeight * 0.5;
  var qrcodeEl = document.getElementById('qrcode')
  drawQr(size, qrcodeEl, state.progress.qrcode);
  qrcodeEl.style.width = size + 'px';
  qrcodeEl.style.height = size + 'px';

  qrcodeEl.addEventListener('click', function () {
    window.location.href = state.progress.qrcode;
  });
  var parts = state.progress.qrcode.split('/ipfs/');
  if (parts.length == 1) {
    var qrString = state.progress.qrcode;
  } else {
    var qrString = parts[0] + '/ipfs/
' + parts[1];
  }
  document.getElementById('address').innerHTML = qrString;
};

var renderProgress = function () {
  var statusEl = document.getElementById('status');
  statusEl.value = state.progress.percent;
};

var determineView = function () {
  if (state.progress.qrcode && state.progress.qrcode !== state.lastShown) {
    state.view = 'result';
    return;
  }
  if (state.progress.percent === 100) {
    state.view = 'welcome';
    return;
  }
  state.view = 'progress';
};

var render = function (address) {
  if (state.timer && state.lastShown && state.lastShown !== state.progress.qrcode) {
    window.clearTimeout(state.timer);
    state.timer = null;
  }
  var welcomeEl = document.getElementById('welcome');
  var progressEl = document.getElementById('progress');
  var resultEl = document.getElementById('result');
  switch (state.view) {
    case 'welcome':
      progressEl.style.display = 'none';
      resultEl.style.display = 'none';
      welcomeEl.style.display = 'block';
      break;
    case 'progress':
      state.lastShown = null;
      resultEl.style.display = 'none';
      welcomeEl.style.display = 'none';
      progressEl.style.display = 'block'
      renderProgress();
      break;
    case 'result':
      progressEl.style.display = 'none'
      welcomeEl.style.display = 'none';
      resultEl.style.display = 'block';
      renderQr();
      state.timer = window.setTimeout(function () {
        state.view = 'welcome';
        state.lastShown = state.progress.qrcode;
        state.progress.qrcode = null;
        render();
      }, 240 * 1000);
      break;
  }
  var messageEl = document.getElementById('message');
  if (state.view !== 'welcome' || state.progress.message && state.progress.message.indexOf('Error') !== -1) {
    messageEl.innerHTML = state.progress.message;
    state.progress.lastMessageShown = state.progress.message;
  } else {
    messageEl.innerHTML = '';
  }
  document.body.className = state.view;
};

var address = 'http://siri.cbrp3.c-base.org/deaddrop.json';
if (window.location.search) {
  address = window.location.search.substr(1);
}
state.url = address;

document.addEventListener('DOMContentLoaded', function () {
  render();
  setInterval(function () {
    fetchState();
  }, 1000);
  fetchState();
});
window.addEventListener('resize', function () {
  render();
});

var fetchState = function () {
  var req = new XMLHttpRequest;
  req.open('GET', state.url, true);
  req.onload  = function() {
    if (req.readyState !== 4) {
      return;
    }
    if (req.status === 200) {
      try {
        state.progress = JSON.parse(req.responseText);
      } catch (e) {
        state.progress.message = "Error parsing server file";
      }
      determineView();
      render();
    }
  };
  req.send(null);
};
<|endoftext|>


<commit_before>/* eslint-disable
    max-len,
    no-return-assign,
    no-useless-escape,
*/
// TODO: This file was created by bulk-decaffeinate.
// Fix any style issues and re-enable lint.
/*
 * decaffeinate suggestions:
 * DS101: Remove unnecessary use of Array.from
 * DS102: Remove unnecessary code created because of implicit returns
 * DS207: Consider shorter variations of null checks
 * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md
 */
import App from '../../base'
import _ from 'lodash'
import '../../vendor/libs/jquery-layout'
import '../../vendor/libs/jquery.ui.touch-punch'

export default App.directive('layout', ($parse, $compile, ide) => ({
  compile() {
    return {
      pre(scope, element, attrs) {
        let customTogglerEl, spacingClosed, spacingOpen, state
        const name = attrs.layout

        const { customTogglerPane } = attrs
        const { customTogglerMsgWhenOpen } = attrs
        const { customTogglerMsgWhenClosed } = attrs
        const hasCustomToggler =
          customTogglerPane != null &&
          customTogglerMsgWhenOpen != null &&
          customTogglerMsgWhenClosed != null

        if (attrs.spacingOpen != null) {
          spacingOpen = parseInt(attrs.spacingOpen, 10)
        } else {
          spacingOpen = 7
        }

        if (attrs.spacingClosed != null) {
          spacingClosed = parseInt(attrs.spacingClosed, 10)
        } else {
          spacingClosed = 7
        }

        const options = {
          spacing_open: spacingOpen,
          spacing_closed: spacingClosed,
          slidable: false,
          enableCursorHotkey: false,
          onopen: pane => {
            return onPaneOpen(pane)
          },
          onclose: pane => {
            return onPaneClose(pane)
          },
          onresize: () => {
            return onInternalResize()
          },
          maskIframesOnResize: scope.$eval(
            attrs.maskIframesOnResize || 'false'
          ),
          east: {
            size: scope.$eval(attrs.initialSizeEast),
            initClosed: scope.$eval(attrs.initClosedEast),
          },
          west: {
            size: scope.$eval(attrs.initialSizeEast),
            initClosed: scope.$eval(attrs.initClosedWest),
          },
        }

        // Restore previously recorded state
        if ((state = ide.localStorage(`layout.${name}`)) != null) {
          if (state.east != null) {
            if (
              attrs.minimumRestoreSizeEast == null ||
              (state.east.size >= attrs.minimumRestoreSizeEast &&
                !state.east.initClosed)
            ) {
              options.east = state.east
            }
          }
          if (state.west != null) {
            if (
              attrs.minimumRestoreSizeWest == null ||
              (state.west.size >= attrs.minimumRestoreSizeWest &&
                !state.west.initClosed)
            ) {
              options.west = state.west
            }
          }
        }

        options.east.resizerCursor = 'ew-resize'
        options.west.resizerCursor = 'ew-resize'

        const repositionControls = function () {
          state = element.layout().readState()
          if (state.east != null) {
            const controls = element.find('> .ui-layout-resizer-controls')
            if (state.east.initClosed) {
              return controls.hide()
            } else {
              controls.show()
              return controls.css({
                right: state.east.size,
              })
            }
          }
        }

        const repositionCustomToggler = function () {
          if (customTogglerEl == null) {
            return
          }
          state = element.layout().readState()
          const positionAnchor = customTogglerPane === 'east' ? 'right' : 'left'
          const paneState = state[customTogglerPane]
          if (paneState != null) {
            return customTogglerEl.css(
              positionAnchor,
              paneState.initClosed ? 0 : paneState.size
            )
          }
        }

        const resetOpenStates = function () {
          state = element.layout().readState()
          if (attrs.openEast != null && state.east != null) {
            const openEast = $parse(attrs.openEast)
            return openEast.assign(scope, !state.east.initClosed)
          }
        }

        // Someone moved the resizer
        function onInternalResize() {
          state = element.layout().readState()
          scope.$broadcast(`layout:${name}:resize`, state)
          repositionControls()
          if (hasCustomToggler) {
            repositionCustomToggler()
          }
          return resetOpenStates()
        }

        let oldWidth = element.width()
        // Something resized our parent element
        const onExternalResize = function () {
          if (
            attrs.resizeProportionally != null &&
            scope.$eval(attrs.resizeProportionally)
          ) {
            const eastState = element.layout().readState().east
            if (eastState != null) {
              const newInternalWidth =
                (eastState.size / oldWidth) * element.width()
              oldWidth = element.width()
              element.layout().sizePane('east', newInternalWidth)
              return
            }
          }

          ide.$timeout(() => {
            element.layout().resizeAll()
          })
        }

        element.layout(options)
        element.layout().resizeAll()

        if (attrs.resizeOn != null) {
          for (const event of Array.from(attrs.resizeOn.split(','))) {
            scope.$on(event, () => onExternalResize())
          }
        }

        if (hasCustomToggler) {
          state = element.layout().readState()
          const customTogglerScope = scope.$new()

          customTogglerScope.isOpen = true
          customTogglerScope.isVisible = true

          if (
            (state[customTogglerPane] != null
              ? state[customTogglerPane].initClosed
              : undefined) === true
          ) {
            customTogglerScope.isOpen = false
          }

          customTogglerScope.tooltipMsgWhenOpen = customTogglerMsgWhenOpen
          customTogglerScope.tooltipMsgWhenClosed = customTogglerMsgWhenClosed

          customTogglerScope.tooltipPlacement =
            customTogglerPane === 'east' ? 'left' : 'right'
          customTogglerScope.handleClick = function () {
            element.layout().toggle(customTogglerPane)
            return repositionCustomToggler()
          }
          customTogglerEl = $compile(`\
<a href \
ng-show=\"isVisible\" \
class=\"custom-toggler ${`custom-toggler-${customTogglerPane}`}\" \
ng-class=\"isOpen ? 'custom-toggler-open' : 'custom-toggler-closed'\" \
tooltip=\"{{ isOpen ? tooltipMsgWhenOpen : tooltipMsgWhenClosed }}\" \
tooltip-placement=\"{{ tooltipPlacement }}\" \
ng-click=\"handleClick()\">\
`)(customTogglerScope)
          element.append(customTogglerEl)
        }

        function onPaneOpen(pane) {
          if (!hasCustomToggler && pane !== customTogglerPane) {
            return
          }
          return customTogglerEl
            .scope()
            .$applyAsync(() => (customTogglerEl.scope().isOpen = true))
        }

        function onPaneClose(pane) {
          if (!hasCustomToggler && pane !== customTogglerPane) {
            return
          }
          return customTogglerEl
            .scope()
            .$applyAsync(() => (customTogglerEl.scope().isOpen = false))
        }

        // Save state when exiting
        $(window).unload(() => {
          // Save only the state properties for the current layout, ignoring sublayouts inside it.
          // If we save sublayouts state (`children`), the layout library will use it when
          // initializing. This raises errors when the sublayout elements aren't available (due to
          // being loaded at init or just not existing for the current project/user).
          const stateToSave = _.mapValues(element.layout().readState(), pane =>
            _.omit(pane, 'children')
          )
          ide.localStorage(`layout.${name}`, stateToSave)
        })

        if (attrs.openEast != null) {
          scope.$watch(attrs.openEast, function (value, oldValue) {
            if (value != null && value !== oldValue) {
              if (value) {
                element.layout().open('east')
              } else {
                element.layout().close('east')
              }
            }
            return setTimeout(() => scope.$digest(), 0)
          })
        }

        if (attrs.allowOverflowOn != null) {
          const layoutObj = element.layout()
          const overflowPane = scope.$eval(attrs.allowOverflowOn)
          const overflowPaneEl = layoutObj.panes[overflowPane]
          // Set the panel as overflowing (gives it higher z-index and sets overflow rules)
          layoutObj.allowOverflow(overflowPane)
          // Read the given z-index value and increment it, so that it's higher than synctex controls.
          const overflowPaneZVal = overflowPaneEl.zIndex()
          overflowPaneEl.css('z-index', overflowPaneZVal + 1)
        }

        resetOpenStates()
        onInternalResize()

        if (attrs.layoutDisabled != null) {
          return scope.$watch(attrs.layoutDisabled, function (value) {
            if (value) {
              element.layout().hide('east')
            } else {
              element.layout().show('east')
            }
            if (hasCustomToggler) {
              return customTogglerEl.scope().$applyAsync(function () {
                customTogglerEl.scope().isOpen = !value
                return (customTogglerEl.scope().isVisible = !value)
              })
            }
          })
        }
      },

      post(scope, element, attrs) {
        const name = attrs.layout
        const state = element.layout().readState()
        return scope.$broadcast(`layout:${name}:linked`, state)
      },
    }
  },
}))
<commit_msg>Reduce calls to jQuery layout() (#7994)<commit_after>/* eslint-disable
    max-len,
    no-return-assign,
    no-useless-escape,
*/
// TODO: This file was created by bulk-decaffeinate.
// Fix any style issues and re-enable lint.
/*
 * decaffeinate suggestions:
 * DS101: Remove unnecessary use of Array.from
 * DS102: Remove unnecessary code created because of implicit returns
 * DS207: Consider shorter variations of null checks
 * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md
 */
import App from '../../base'
import _ from 'lodash'
import '../../vendor/libs/jquery-layout'
import '../../vendor/libs/jquery.ui.touch-punch'

export default App.directive('layout', ($parse, $compile, ide) => ({
  compile() {
    return {
      pre(scope, element, attrs) {
        let customTogglerEl, spacingClosed, spacingOpen, state
        const name = attrs.layout

        const { customTogglerPane } = attrs
        const { customTogglerMsgWhenOpen } = attrs
        const { customTogglerMsgWhenClosed } = attrs
        const hasCustomToggler =
          customTogglerPane != null &&
          customTogglerMsgWhenOpen != null &&
          customTogglerMsgWhenClosed != null

        if (attrs.spacingOpen != null) {
          spacingOpen = parseInt(attrs.spacingOpen, 10)
        } else {
          spacingOpen = 7
        }

        if (attrs.spacingClosed != null) {
          spacingClosed = parseInt(attrs.spacingClosed, 10)
        } else {
          spacingClosed = 7
        }

        const options = {
          spacing_open: spacingOpen,
          spacing_closed: spacingClosed,
          slidable: false,
          enableCursorHotkey: false,
          onopen: pane => {
            return onPaneOpen(pane)
          },
          onclose: pane => {
            return onPaneClose(pane)
          },
          onresize: () => {
            return onInternalResize()
          },
          maskIframesOnResize: scope.$eval(
            attrs.maskIframesOnResize || 'false'
          ),
          east: {
            size: scope.$eval(attrs.initialSizeEast),
            initClosed: scope.$eval(attrs.initClosedEast),
          },
          west: {
            size: scope.$eval(attrs.initialSizeEast),
            initClosed: scope.$eval(attrs.initClosedWest),
          },
        }

        // Restore previously recorded state
        if ((state = ide.localStorage(`layout.${name}`)) != null) {
          if (state.east != null) {
            if (
              attrs.minimumRestoreSizeEast == null ||
              (state.east.size >= attrs.minimumRestoreSizeEast &&
                !state.east.initClosed)
            ) {
              options.east = state.east
            }
          }
          if (state.west != null) {
            if (
              attrs.minimumRestoreSizeWest == null ||
              (state.west.size >= attrs.minimumRestoreSizeWest &&
                !state.west.initClosed)
            ) {
              options.west = state.west
            }
          }
        }

        options.east.resizerCursor = 'ew-resize'
        options.west.resizerCursor = 'ew-resize'

        function repositionControls() {
          state = layout.readState()
          if (state.east != null) {
            const controls = element.find('> .ui-layout-resizer-controls')
            if (state.east.initClosed) {
              return controls.hide()
            } else {
              controls.show()
              return controls.css({
                right: state.east.size,
              })
            }
          }
        }

        function repositionCustomToggler() {
          if (customTogglerEl == null) {
            return
          }
          state = layout.readState()
          const positionAnchor = customTogglerPane === 'east' ? 'right' : 'left'
          const paneState = state[customTogglerPane]
          if (paneState != null) {
            return customTogglerEl.css(
              positionAnchor,
              paneState.initClosed ? 0 : paneState.size
            )
          }
        }

        function resetOpenStates() {
          state = layout.readState()
          if (attrs.openEast != null && state.east != null) {
            const openEast = $parse(attrs.openEast)
            return openEast.assign(scope, !state.east.initClosed)
          }
        }

        // Someone moved the resizer
        function onInternalResize() {
          state = layout.readState()
          scope.$broadcast(`layout:${name}:resize`, state)
          repositionControls()
          if (hasCustomToggler) {
            repositionCustomToggler()
          }
          return resetOpenStates()
        }

        let oldWidth = element.width()
        // Something resized our parent element
        const onExternalResize = function () {
          if (
            attrs.resizeProportionally != null &&
            scope.$eval(attrs.resizeProportionally)
          ) {
            const eastState = layout.readState().east
            if (eastState != null) {
              const newInternalWidth =
                (eastState.size / oldWidth) * element.width()
              oldWidth = element.width()
              layout.sizePane('east', newInternalWidth)
              return
            }
          }

          ide.$timeout(() => {
            layout.resizeAll()
          })
        }

        const layout = element.layout(options)
        layout.resizeAll()

        if (attrs.resizeOn != null) {
          for (const event of Array.from(attrs.resizeOn.split(','))) {
            scope.$on(event, () => onExternalResize())
          }
        }

        if (hasCustomToggler) {
          state = layout.readState()
          const customTogglerScope = scope.$new()

          customTogglerScope.isOpen = true
          customTogglerScope.isVisible = true

          if (
            (state[customTogglerPane] != null
              ? state[customTogglerPane].initClosed
              : undefined) === true
          ) {
            customTogglerScope.isOpen = false
          }

          customTogglerScope.tooltipMsgWhenOpen = customTogglerMsgWhenOpen
          customTogglerScope.tooltipMsgWhenClosed = customTogglerMsgWhenClosed

          customTogglerScope.tooltipPlacement =
            customTogglerPane === 'east' ? 'left' : 'right'
          customTogglerScope.handleClick = function () {
            layout.toggle(customTogglerPane)
            return repositionCustomToggler()
          }
          customTogglerEl = $compile(`\
<a href \
ng-show=\"isVisible\" \
class=\"custom-toggler ${`custom-toggler-${customTogglerPane}`}\" \
ng-class=\"isOpen ? 'custom-toggler-open' : 'custom-toggler-closed'\" \
tooltip=\"{{ isOpen ? tooltipMsgWhenOpen : tooltipMsgWhenClosed }}\" \
tooltip-placement=\"{{ tooltipPlacement }}\" \
ng-click=\"handleClick()\">\
`)(customTogglerScope)
          element.append(customTogglerEl)
        }

        function onPaneOpen(pane) {
          if (!hasCustomToggler && pane !== customTogglerPane) {
            return
          }
          return customTogglerEl
            .scope()
            .$applyAsync(() => (customTogglerEl.scope().isOpen = true))
        }

        function onPaneClose(pane) {
          if (!hasCustomToggler && pane !== customTogglerPane) {
            return
          }
          return customTogglerEl
            .scope()
            .$applyAsync(() => (customTogglerEl.scope().isOpen = false))
        }

        // Save state when exiting
        $(window).unload(() => {
          // Save only the state properties for the current layout, ignoring sublayouts inside it.
          // If we save sublayouts state (`children`), the layout library will use it when
          // initializing. This raises errors when the sublayout elements aren't available (due to
          // being loaded at init or just not existing for the current project/user).
          const stateToSave = _.mapValues(layout.readState(), pane =>
            _.omit(pane, 'children')
          )
          ide.localStorage(`layout.${name}`, stateToSave)
        })

        if (attrs.openEast != null) {
          scope.$watch(attrs.openEast, function (value, oldValue) {
            if (value != null && value !== oldValue) {
              if (value) {
                layout.open('east')
              } else {
                layout.close('east')
              }
            }
            return setTimeout(() => scope.$digest(), 0)
          })
        }

        if (attrs.allowOverflowOn != null) {
          const overflowPane = scope.$eval(attrs.allowOverflowOn)
          const overflowPaneEl = layout.panes[overflowPane]
          // Set the panel as overflowing (gives it higher z-index and sets overflow rules)
          layout.allowOverflow(overflowPane)
          // Read the given z-index value and increment it, so that it's higher than synctex controls.
          const overflowPaneZVal = overflowPaneEl.zIndex()
          overflowPaneEl.css('z-index', overflowPaneZVal + 1)
        }

        resetOpenStates()
        onInternalResize()

        if (attrs.layoutDisabled != null) {
          return scope.$watch(attrs.layoutDisabled, function (value) {
            if (value) {
              layout.hide('east')
            } else {
              layout.show('east')
            }
            if (hasCustomToggler) {
              return customTogglerEl.scope().$applyAsync(function () {
                customTogglerEl.scope().isOpen = !value
                return (customTogglerEl.scope().isVisible = !value)
              })
            }
          })
        }
      },

      post(scope, element, attrs) {
        const name = attrs.layout
        const state = element.layout().readState()
        return scope.$broadcast(`layout:${name}:linked`, state)
      },
    }
  },
}))
<|endoftext|>


<commit_before>#!/usr/bin/env node

var fs = require('fs'),
    parse = require('csv-parse'),
    _ = require('underscore'),
    moment = require('moment'),
    db = require('./db'),
    csvOptions = {columns: true},
    currentCommittees = {},
    batchSize = 10,
    committeeTableName = 'committees',
    contributionTableName = 'contributions',
    expenditureTableName = 'expenditures',
    abbrev = {
        STREET: 'ST',
        ROAD: 'RD',
        DRIVE: 'DR',
        AVENUE: 'AVE',
        COURT: 'CT',
        LANE: 'LN',
        TERRACE: 'TER',
        CIRCLE: 'CIR',
        BOULEVARD: 'BLVD',
        HIGHWAY: 'HWY',
        PLACE: 'PL'
    },
    abbrevRegexp = new RegExp('\\b(' + Object.keys(abbrev).join('|') + ')\\b');

db.schema.dropTableIfExists(contributionTableName)
    .dropTableIfExists(expenditureTableName)
    .dropTableIfExists(committeeTableName)
    .createTable(
        committeeTableName,
        function (table) {
            var columnNames = [
                'committee_name',
                'candidate_name',
                'election_year',
                'status',
                'office'
            ];
            table.increments();
            columnNames.forEach(function (columnName) {
                if (/year/.test(columnName)) {
                    table.integer(columnName);
                }
                else {
                    table.string(columnName);
                }
            });
        }
    )
    .createTable(
        contributionTableName,
        function (table) {
            var columnNames = [
                    'committee_name',
                    'contributor_name',
                    'contributor_address',
                    'normalized',
                    'contributor_state',
                    'contributor_type',
                    'contribution_type',
                    'employer_name',
                    'employer_address',
                    'occupation',
                    'receipt_date',
                    'amount'
                ];
            table.increments();
            columnNames.forEach(function (columnName) {
                if (/date/.test(columnName)) {
                    table.date(columnName);
                }
                else if (/amount|total/.test(columnName)) {
                    table.float(columnName);
                }
                else {
                    table.string(columnName);
                }
            });
        }
    )
    .createTable(
        expenditureTableName,
        function (table) {
            var columnNames = [
                'committee_name',
                'payee_name',
                'payee_address',
                'normalized',
                'purpose_of_expenditure',
                'payment_date',
                'amount'
            ];
            table.increments();
            columnNames.forEach(function (columnName) {
                if (/date/.test(columnName)) {
                    table.date(columnName);
                }
                else if (/amount|total/.test(columnName)) {
                    table.float(columnName);
                }
                else {
                    table.string(columnName);
                }
            });
        }
    )
    .then(readCommittees);

function readCommittees() {
    var parser = parse(csvOptions),
        input = fs.createReadStream(__dirname + '/' + committeeTableName + '.csv'),
        records = [];
    parser.on('readable', function () {
        var record;
        while(record = parser.read()) {
            record = transformRecord(record);
            currentCommittees[record.committee_name] = true;
            records.push(record);
        }
    });
    parser.on('error', function (err) {
        console.error(err.message);
        throw err;
    });
    parser.on('finish', function () {
        console.log('Finished reading committees');
        console.log(Object.keys(currentCommittees).sort());
        db.batchInsert(committeeTableName, records, batchSize)
            .returning('id')
            .then(readContributions);
    });
    input.pipe(parser);
}

function readContributions() {
    var parser = parse(csvOptions),
        input = fs.createReadStream(__dirname + '/' + contributionTableName + '.csv'),
        seen = {},
        unrecognized = [],
        totalCount = 0,
        currentCount = 0,
        batch = [];
    parser.on('readable', function () {
        var record;
        while (record = parser.read()) {
            var name, m;
            totalCount++;
            record = transformRecord(record);
            name = record.committee_name;
            if (!seen[name]) {
                seen[name] = true;
                console.log(name);
                if (!currentCommittees[name]) {
                    unrecognized.push(name);
                }
            }
            if (!currentCommittees[name]) {
                continue;
            }
            record.normalized = normalizeNameAndAddress(record.contributor_name, record.contributor_address);
            if (m = record.normalized.match(/ ([A-Z]{2})$/)) {
                record.contributor_state = m[1];
            }
            else {
                record.contributor_state = '';
            }
            batch.push(record);
            if (batch.length >= 10000) {
                db.batchInsert(contributionTableName, batch, batchSize)
                    .then(function () {});
                batch = [];
            }
            currentCount++;
        }
    });
    parser.on('error', function (err) {
        console.error(err.message);
        throw err;
    });
    parser.on('finish', function () {
        if (batch.length) {
            db.batchInsert(contributionTableName, batch, batchSize)
                .then(function () {});
        }
        console.log('Finished reading %d contributions', totalCount);
        console.log('Inserted %d contributions', currentCount);
        console.log('Unrecognized committees:\n', unrecognized.sort());
        readExpenditures();
    });
    input.pipe(parser);
}

function readExpenditures() {
    var parser = parse(csvOptions),
        input = fs.createReadStream(__dirname + '/' + expenditureTableName + '.csv'),
        seen = {},
        unrecognized = [],
        totalCount = 0,
        currentCount = 0,
        batch = [];
    parser.on('readable', function () {
        var record;
        while (record = parser.read()) {
            var name;
            totalCount++;
            record = transformRecord(record);
            name = record.committee_name;
            if (!seen[name]) {
                seen[name] = true;
                console.log(name);
                if (!currentCommittees[name]) {
                    unrecognized.push(name);
                }
            }
            if (!currentCommittees[name]) {
                continue;
            }
            record.normalized = normalizeNameAndAddress(record.payee_name, record.payee_address);
            batch.push(record);
            if (batch.length >= 10000) {
                db.batchInsert(expenditureTableName, batch, batchSize)
                    .then(function () {});
                batch = [];
            }
            currentCount++;
        }
    });
    parser.on('error', function (err) {
        console.error(err.message);
        throw err;
    });
    parser.on('finish', function () {
        if (batch.length) {
            db.batchInsert(expenditureTableName, batch, batchSize)
                .then(finish);
        }
        else {
            finish();
        }

        function finish() {
            console.log('Finished reading %d expenditures', totalCount);
            console.log('Inserted %d expenditures', currentCount);
            //console.log('Unrecognized committees:\n', unrecognized.sort());
            addDummyContributions();
        }
    });
    input.pipe(parser);
}

// Add negative contributions corresponding to refunds and bounced checks
function addDummyContributions() {
    db.select(
            'e.committee_name',
            'e.payee_name as contributor_name',
            'e.payee_address as contributor_address',
            'e.normalized',
            'c.contributor_state',
            'c.contributor_type',
            'e.purpose_of_expenditure as contribution_type',
            'c.employer_name',
            'c.employer_address',
            'c.occupation',
            'e.payment_date as receipt_date',
            db.raw('-e.amount as amount')
        )
        .from('expenditures as e')
        .innerJoin('contributions as c', function () {
            this.on('e.committee_name', 'c.committee_name')
                .andOn('e.normalized', 'c.normalized')
        })
        .whereIn('purpose_of_expenditure', ['Refund', 'Return Check and Fees'])
        .groupBy('e.id')
        .orderBy('e.committee_name')
        .orderBy('e.payee_name')
        .then(function (rows) {
            db.batchInsert(contributionTableName, rows, batchSize)
                .then(function () {
                    console.log('Dummy contributions inserted');
                    process.exit();
                });
        })
}

function transformRecord(record) {
    var newRecord = {};
    _.each(record, function (value, key) {
        value = trim(value);
        key = nameToCode(key);
        if (/date/.test(key) && /^\d\d?\/\d\d?\/\d{4}$/.test(value)) {
            value = moment(value, 'MM/DD/YYYY').format('YYYY-MM-DD');
        }
        else if (/amount|total/.test(key) && /^[\$\.,\d]+$/.test(value)) {
            value = value.replace(/[\$,]/g, '');
        }
        newRecord[key] = value;
    });
    return newRecord;
}

function nameToCode(s) {
    return s.toLowerCase()
        .replace(/\W+/g, '_')
        .replace(/^_|_$/g, '');
}

function trim(s) {
    return s ? s.replace(/\s+/g, ' ').replace(/^ | $/g, '') : '';
}

function normalizeNameAndAddress(name, address) {
    var normalized = name.toUpperCase()
        .replace(/[ ,]*,[ ,]*/g, ' ')
        .replace(/\./g, '')
        .replace(/^(MR|MS|MRS|DR) /, '')
        .replace(/ AND /g, ' & ')
        .replace(/^THE /, '')
//        .replace(/ [A-Z] /g, ' ') // remove middle initials
//        .replace(/ (JR|SR|I{1,3})$/, '')
        .replace(/[\- ]*\-[\- ]*/g, ' ');
    if (address) {
        normalized += ', ' + address.toUpperCase()
            .replace(/[ ,]*,[ ,]*/g, ' ')
            .replace(/\./g, '')
            .replace(/'/g, '')
            .replace(/,?\s*([NS][EW],)/, ' $1')
            .replace(/ [\d \-]+$/, '') // remove zip
            .replace(/[\- ]*\-[\- ]*/g, ' ')
            .replace(/\b(SUITE|STE|APT|UNIT)[ #]+/, '#')
            .replace(/# /, '#')
            .replace(/ FL(?:OOR)? \d\d?(?:[NR]?D|ST|TH)? /, ' ')
            .replace(/ \d\d?(?:[NR]?D|ST|TH)? FL(?:OOR)? /, ' ')
            .replace(/ VIRGINIA$/, ' VA')
            .replace(/ MARYLAND$/, ' MD')
            .replace(/ DISTRICT OF COLUMBIA$/, ' DC')
            .replace(/ MC LEAN /g, ' MCLEAN ')
            .replace(/( \w+)(\1 [A-Z]{2})$/, '$2')
            .replace(/( \w+ [A-Z]{2})\1$/, '$1')
            .replace(/ #\S+/, '') // remove apartment number
            .replace(abbrevRegexp, function (m, p1) {
                return abbrev[p1];
            });
    }
    return normalized;
}
<commit_msg>Add missing fields<commit_after>#!/usr/bin/env node

var fs = require('fs'),
    parse = require('csv-parse'),
    _ = require('underscore'),
    moment = require('moment'),
    db = require('./db'),
    csvOptions = {columns: true},
    currentCommittees = {},
    batchSize = 10,
    committeeTableName = 'committees',
    contributionTableName = 'contributions',
    expenditureTableName = 'expenditures',
    abbrev = {
        STREET: 'ST',
        ROAD: 'RD',
        DRIVE: 'DR',
        AVENUE: 'AVE',
        COURT: 'CT',
        LANE: 'LN',
        TERRACE: 'TER',
        CIRCLE: 'CIR',
        BOULEVARD: 'BLVD',
        HIGHWAY: 'HWY',
        PLACE: 'PL'
    },
    abbrevRegexp = new RegExp('\\b(' + Object.keys(abbrev).join('|') + ')\\b');

db.schema.dropTableIfExists(contributionTableName)
    .dropTableIfExists(expenditureTableName)
    .dropTableIfExists(committeeTableName)
    .createTable(
        committeeTableName,
        function (table) {
            var columnNames = [
                'committee_name',
                'candidate_name',
                'election_year',
                'status',
                'office'
            ];
            table.increments();
            columnNames.forEach(function (columnName) {
                if (/year/.test(columnName)) {
                    table.integer(columnName);
                }
                else {
                    table.string(columnName);
                }
            });
        }
    )
    .createTable(
        contributionTableName,
        function (table) {
            var columnNames = [
                    'committee_name',
                    'contributor_name',
                    'contributor_address',
                    'number_and_street',
                    'city',
                    'state',
                    'zip',
                    'normalized',
                    'contributor_state',
                    'contributor_type',
                    'contribution_type',
                    'employer_name',
                    'employer_address',
                    'occupation',
                    'receipt_date',
                    'amount'
                ];
            table.increments();
            columnNames.forEach(function (columnName) {
                if (/date/.test(columnName)) {
                    table.date(columnName);
                }
                else if (/amount|total/.test(columnName)) {
                    table.float(columnName);
                }
                else {
                    table.string(columnName);
                }
            });
        }
    )
    .createTable(
        expenditureTableName,
        function (table) {
            var columnNames = [
                'committee_name',
                'payee_name',
                'payee_address',
                'normalized',
                'purpose_of_expenditure',
                'payment_date',
                'number_and_street',
                'city',
                'state',
                'zip',
                'amount'
            ];
            table.increments();
            columnNames.forEach(function (columnName) {
                if (/date/.test(columnName)) {
                    table.date(columnName);
                }
                else if (/amount|total/.test(columnName)) {
                    table.float(columnName);
                }
                else {
                    table.string(columnName);
                }
            });
        }
    )
    .then(readCommittees);

function readCommittees() {
    var parser = parse(csvOptions),
        input = fs.createReadStream(__dirname + '/' + committeeTableName + '.csv'),
        records = [];
    parser.on('readable', function () {
        var record;
        while(record = parser.read()) {
            record = transformRecord(record);
            currentCommittees[record.committee_name] = true;
            records.push(record);
        }
    });
    parser.on('error', function (err) {
        console.error(err.message);
        throw err;
    });
    parser.on('finish', function () {
        console.log('Finished reading committees');
        console.log(Object.keys(currentCommittees).sort());
        db.batchInsert(committeeTableName, records, batchSize)
            .returning('id')
            .then(readContributions);
    });
    input.pipe(parser);
}

function readContributions() {
    var parser = parse(csvOptions),
        input = fs.createReadStream(__dirname + '/' + contributionTableName + '.csv'),
        seen = {},
        unrecognized = [],
        totalCount = 0,
        currentCount = 0,
        batch = [];
    parser.on('readable', function () {
        var record;
        while (record = parser.read()) {
            var name, m;
            totalCount++;
            record = transformRecord(record);
            name = record.committee_name;
            if (!seen[name]) {
                seen[name] = true;
                console.log(name);
                if (!currentCommittees[name]) {
                    unrecognized.push(name);
                }
            }
            if (!currentCommittees[name]) {
                continue;
            }
            record.normalized = normalizeNameAndAddress(record.contributor_name, record.contributor_address);
            if (m = record.normalized.match(/ ([A-Z]{2})$/)) {
                record.contributor_state = m[1];
            }
            else {
                record.contributor_state = '';
            }
            batch.push(record);
            if (batch.length >= 10000) {
                db.batchInsert(contributionTableName, batch, batchSize)
                    .then(function () {});
                batch = [];
            }
            currentCount++;
        }
    });
    parser.on('error', function (err) {
        console.error(err.message);
        throw err;
    });
    parser.on('finish', function () {
        if (batch.length) {
            db.batchInsert(contributionTableName, batch, batchSize)
                .then(function () {});
        }
        console.log('Finished reading %d contributions', totalCount);
        console.log('Inserted %d contributions', currentCount);
        console.log('Unrecognized committees:\n', unrecognized.sort());
        readExpenditures();
    });
    input.pipe(parser);
}

function readExpenditures() {
    var parser = parse(csvOptions),
        input = fs.createReadStream(__dirname + '/' + expenditureTableName + '.csv'),
        seen = {},
        unrecognized = [],
        totalCount = 0,
        currentCount = 0,
        batch = [];
    parser.on('readable', function () {
        var record;
        while (record = parser.read()) {
            var name;
            totalCount++;
            record = transformRecord(record);
            name = record.committee_name;
            if (!seen[name]) {
                seen[name] = true;
                console.log(name);
                if (!currentCommittees[name]) {
                    unrecognized.push(name);
                }
            }
            if (!currentCommittees[name]) {
                continue;
            }
            record.normalized = normalizeNameAndAddress(record.payee_name, record.payee_address);
            batch.push(record);
            if (batch.length >= 10000) {
                db.batchInsert(expenditureTableName, batch, batchSize)
                    .then(function () {});
                batch = [];
            }
            currentCount++;
        }
    });
    parser.on('error', function (err) {
        console.error(err.message);
        throw err;
    });
    parser.on('finish', function () {
        if (batch.length) {
            db.batchInsert(expenditureTableName, batch, batchSize)
                .then(finish);
        }
        else {
            finish();
        }

        function finish() {
            console.log('Finished reading %d expenditures', totalCount);
            console.log('Inserted %d expenditures', currentCount);
            //console.log('Unrecognized committees:\n', unrecognized.sort());
            addDummyContributions();
        }
    });
    input.pipe(parser);
}

// Add negative contributions corresponding to refunds and bounced checks
function addDummyContributions() {
    db.select(
            'e.committee_name',
            'e.payee_name as contributor_name',
            'e.payee_address as contributor_address',
            'e.normalized',
            'c.contributor_state',
            'c.contributor_type',
            'e.purpose_of_expenditure as contribution_type',
            'c.employer_name',
            'c.employer_address',
            'c.occupation',
            'e.payment_date as receipt_date',
            db.raw('-e.amount as amount')
        )
        .from('expenditures as e')
        .innerJoin('contributions as c', function () {
            this.on('e.committee_name', 'c.committee_name')
                .andOn('e.normalized', 'c.normalized')
        })
        .whereIn('purpose_of_expenditure', ['Refund', 'Return Check and Fees'])
        .groupBy('e.id')
        .orderBy('e.committee_name')
        .orderBy('e.payee_name')
        .then(function (rows) {
            db.batchInsert(contributionTableName, rows, batchSize)
                .then(function () {
                    console.log('Dummy contributions inserted');
                    process.exit();
                });
        })
}

function transformRecord(record) {
    var newRecord = {};
    _.each(record, function (value, key) {
        value = trim(value);
        key = nameToCode(key);
        if (/date/.test(key) && /^\d\d?\/\d\d?\/\d{4}$/.test(value)) {
            value = moment(value, 'MM/DD/YYYY').format('YYYY-MM-DD');
        }
        else if (/amount|total/.test(key) && /^[\$\.,\d]+$/.test(value)) {
            value = value.replace(/[\$,]/g, '');
        }
        newRecord[key] = value;
    });
    return newRecord;
}

function nameToCode(s) {
    return s.toLowerCase()
        .replace(/\W+/g, '_')
        .replace(/^_|_$/g, '');
}

function trim(s) {
    return s ? s.replace(/\s+/g, ' ').replace(/^ | $/g, '') : '';
}

function normalizeNameAndAddress(name, address) {
    var normalized = name.toUpperCase()
        .replace(/[ ,]*,[ ,]*/g, ' ')
        .replace(/\./g, '')
        .replace(/^(MR|MS|MRS|DR) /, '')
        .replace(/ AND /g, ' & ')
        .replace(/^THE /, '')
//        .replace(/ [A-Z] /g, ' ') // remove middle initials
//        .replace(/ (JR|SR|I{1,3})$/, '')
        .replace(/[\- ]*\-[\- ]*/g, ' ');
    if (address) {
        normalized += ', ' + address.toUpperCase()
            .replace(/[ ,]*,[ ,]*/g, ' ')
            .replace(/\./g, '')
            .replace(/'/g, '')
            .replace(/,?\s*([NS][EW],)/, ' $1')
            .replace(/ [\d \-]+$/, '') // remove zip
            .replace(/[\- ]*\-[\- ]*/g, ' ')
            .replace(/\b(SUITE|STE|APT|UNIT)[ #]+/, '#')
            .replace(/# /, '#')
            .replace(/ FL(?:OOR)? \d\d?(?:[NR]?D|ST|TH)? /, ' ')
            .replace(/ \d\d?(?:[NR]?D|ST|TH)? FL(?:OOR)? /, ' ')
            .replace(/ VIRGINIA$/, ' VA')
            .replace(/ MARYLAND$/, ' MD')
            .replace(/ DISTRICT OF COLUMBIA$/, ' DC')
            .replace(/ MC LEAN /g, ' MCLEAN ')
            .replace(/( \w+)(\1 [A-Z]{2})$/, '$2')
            .replace(/( \w+ [A-Z]{2})\1$/, '$1')
            .replace(/ #\S+/, '') // remove apartment number
            .replace(abbrevRegexp, function (m, p1) {
                return abbrev[p1];
            });
    }
    return normalized;
}
<|endoftext|>


<commit_before>// For conditions of distribution and use, see copyright notice in LICENSE

(function ( namespace, undefined ) {

    var types = namespace.ENUMS.ATTRIBUTES = namespace.util.createEnum(
        'none', 'string', 'int', 'real', 'color', 'float2', 'float3', 'float4', 'bool', 'uint', 'quat',
        'assetref', 'assetreflist', 'entityref', 'qvariant', 'qvariantlist', 'transform', 'qpoint',
        'numattributetypes'
    );

    var Attribute = namespace.Attribute = function ( name, value, type ) {

        type = type || -1;

        this.type = parseInt( type, 10 );

        this.name = name.replace( /\s/g, '' ).toLowerCase();
        this.val = Attribute.parse( value, this.type );

    };

    Attribute.parse = function ( value, type ) {
        var val = value;

        if ( value !== null /*&& typeof value === "string"*/ ) {

            switch (type) {
                // Int
            case types.real:
            case types.int:
            case types.uint:
                val = Number( value ); //Returns NaN if no legal number representation can be found
                break;

            case types.float3:
            case types.float4:
            case types.quat:
            case types.color:
                val = value.split( / / ).map( parseFloat );
                break;

                // Boolean
            case types.bool:
                val = value === 'true';
                break;

                // Transform
            case types.transform:
                val = value.split( /,/ ).map( parseFloat );
                break;

            case types.string:
            case types.assetref:
                val = value;
                break;

            case types.assetreflist:
                val = value.split( /;/ );
                break;

            default:
                val = null;
                break;

            }
        }

        return val;
    };

    Attribute.prototype.update = function ( value ) {
        var val = Attribute.parse( value, this.type );

        if ( val !== null ) {
            // Just hacky Transform update test

            if ( this.type === types.transform ) {
                for ( var i = val.length; i--; ) {
                    this.val[i] = val[i];
                }
            }
        }
    };

    Attribute.prototype.copy = function ( attr ) {
      if(attr instanceof namespace.Attribute){
          this.type = attr.type;
          this.name = attr.name;
          this.val = attr.val;
      }
    };

}( window['webtundra'] = window['webtundra'] || {} ));
<commit_msg>Added copyValue and attr copy methods to Attribute.js<commit_after>// For conditions of distribution and use, see copyright notice in LICENSE

(function ( namespace, undefined ) {
    var Attribute, types, util;

    util = namespace.util;

    types = namespace.ENUMS.ATTRIBUTES = namespace.util.createEnum(
        'none', 'string', 'int', 'real', 'color', 'float2', 'float3', 'float4', 'bool', 'uint', 'quat',
        'assetref', 'assetreflist', 'entityref', 'qvariant', 'qvariantlist', 'transform', 'qpoint',
        'numattributetypes'
    );

    Attribute = namespace.Attribute = function ( name, value, type ) {

        type = type || -1;

        this.type = parseInt( type, 10 );

        this.name = name.replace( /\s/g, '' ).toLowerCase();
        this.val = Attribute.parse( value, this.type );

    };

    Attribute.parse = function ( value, type ) {
        var val = value;

        if ( value /*&& typeof value === "string"*/ ) {

            switch (type) {
                // Int
            case types.real:
            case types.int:
            case types.uint:
                val = Number( value ); //Returns NaN if no legal number representation can be found
                break;

            case types.float3:
            case types.float4:
            case types.quat:
            case types.color:
                val = value.split( / / ).map( parseFloat );
                break;

                // Boolean
            case types.bool:
                val = value === 'true';
                break;

                // Transform
            case types.transform:
                val = value.split( /,/ ).map( parseFloat );
                break;

            case types.string:
            case types.assetref:
                val = value;
                break;

            case types.assetreflist:
                val = value.split( /;/ );
                break;
            }
        }

        return val;
    };

    Attribute.prototype.update = function ( value ) {
        var val = Attribute.parse( value, this.type );

        if ( val !== undefined ) {
            // Just hacky Transform update test

            if ( this.type === types.transform ) {
                for ( var i = val.length; i--; ) {
                    this.val[i] = val[i];
                }
            }
        }
    };

    Attribute.prototype.copyValue = function ( attr ) {
        var value = attr.val;

        if ( value !== undefined && this.type === attr.type ) {

            if ( value instanceof Array && this.val instanceof Array ) {
                util.extend( this.val, value );
            } else {
                this.val = value;
            }
        }
    };

    Attribute.prototype.copy = function ( attr ) {
        if ( attr instanceof namespace.Attribute ) {
            this.type = attr.type;
            this.name = attr.name;
            this.copyValue( attr );
        }
    };

}( window['webtundra'] = window['webtundra'] || {} ));
<|endoftext|>


<commit_before>describe('Object sources (instead of file paths)', function () {
  'use strict';

  it('should dereference an object that references external files', function () {
    var parser = new SwaggerParser();
    return parser
      .dereference(helper.cloneDeep(helper.parsed.objectSource.api))
      .then(function (api) {
        expect(api).to.equal(parser.api);
        expect(api).to.deep.equal(helper.dereferenced.objectSource);

        // The API path should be blank, and all other paths should be relative (not absolute)
        var expectedPaths = [
          '',
          path.rel('specs/object-source/definitions/definitions.json'),
          path.rel('specs/object-source/definitions/name.yaml'),
          path.rel('specs/object-source/definitions/required-string.yaml')
        ];
        expect(parser.$refs.paths()).to.have.same.members(expectedPaths);
        expect(parser.$refs.values()).to.have.keys(expectedPaths);

        // Reference equality
        expect(api.paths['/people/{name}'].get.responses['200'].schema)
          .to.equal(api.definitions.name);
        expect(api.definitions.requiredString)
          .to.equal(api.definitions.name.properties.first)
          .to.equal(api.definitions.name.properties.last)
          .to.equal(api.paths['/people/{name}'].get.responses['200'].schema.properties.first)
          .to.equal(api.paths['/people/{name}'].get.responses['200'].schema.properties.last);
      });
  });

  it('should bundle an object that references external files', function () {
    var parser = new SwaggerParser();
    return parser
      .bundle(helper.cloneDeep(helper.parsed.objectSource.api))
      .then(function (api) {
        expect(api).to.equal(parser.api);
        expect(api).to.deep.equal(helper.bundled.objectSource);

        // The API path should be blank, and all other paths should be relative (not absolute)
        var expectedPaths = [
          '',
          path.rel('specs/object-source/definitions/definitions.json'),
          path.rel('specs/object-source/definitions/name.yaml'),
          path.rel('specs/object-source/definitions/required-string.yaml')
        ];
        expect(parser.$refs.paths()).to.have.same.members(expectedPaths);
        expect(parser.$refs.values()).to.have.keys(expectedPaths);
      });
  });

  it('should validate an object that references external files', function () {
    var parser = new SwaggerParser();
    return parser
      .dereference(helper.cloneDeep(helper.parsed.objectSource.api))
      .then(function (api) {
        expect(api).to.equal(parser.api);
        expect(api).to.deep.equal(helper.dereferenced.objectSource);

        // The API path should be blank, and all other paths should be relative (not absolute)
        var expectedPaths = [
          '',
          path.rel('specs/object-source/definitions/definitions.json'),
          path.rel('specs/object-source/definitions/name.yaml'),
          path.rel('specs/object-source/definitions/required-string.yaml')
        ];
        expect(parser.$refs.paths()).to.have.same.members(expectedPaths);
        expect(parser.$refs.values()).to.have.keys(expectedPaths);

        // Reference equality
        expect(api.paths['/people/{name}'].get.responses['200'].schema)
          .to.equal(api.definitions.name);
        expect(api.definitions.requiredString)
          .to.equal(api.definitions.name.properties.first)
          .to.equal(api.definitions.name.properties.last)
          .to.equal(api.paths['/people/{name}'].get.responses['200'].schema.properties.first)
          .to.equal(api.paths['/people/{name}'].get.responses['200'].schema.properties.last);
      });
  });
});
<commit_msg>refactored some tests to match the new behavior of JSON Schema $Ref Parser<commit_after>describe('Object sources (instead of file paths)', function () {
  'use strict';

  it('should dereference an object that references external files', function () {
    var parser = new SwaggerParser();
    return parser
      .dereference(helper.cloneDeep(helper.parsed.objectSource.api))
      .then(function (api) {
        expect(api).to.equal(parser.api);
        expect(api).to.deep.equal(helper.dereferenced.objectSource);

        // The API path should be the current directory, and all other paths should be absolute
        var expectedPaths = [
          encodeURI(path.cwd()),
          path.abs('specs/object-source/definitions/definitions.json'),
          path.abs('specs/object-source/definitions/name.yaml'),
          path.abs('specs/object-source/definitions/required-string.yaml')
        ];
        expect(parser.$refs.paths()).to.have.same.members(expectedPaths);
        expect(parser.$refs.values()).to.have.keys(expectedPaths);

        // Reference equality
        expect(api.paths['/people/{name}'].get.responses['200'].schema)
          .to.equal(api.definitions.name);
        expect(api.definitions.requiredString)
          .to.equal(api.definitions.name.properties.first)
          .to.equal(api.definitions.name.properties.last)
          .to.equal(api.paths['/people/{name}'].get.responses['200'].schema.properties.first)
          .to.equal(api.paths['/people/{name}'].get.responses['200'].schema.properties.last);
      });
  });

  it('should bundle an object that references external files', function () {
    var parser = new SwaggerParser();
    return parser
      .bundle(helper.cloneDeep(helper.parsed.objectSource.api))
      .then(function (api) {
        expect(api).to.equal(parser.api);
        expect(api).to.deep.equal(helper.bundled.objectSource);

        // The API path should be the current directory, and all other paths should be absolute
        var expectedPaths = [
          encodeURI(path.cwd()),
          path.abs('specs/object-source/definitions/definitions.json'),
          path.abs('specs/object-source/definitions/name.yaml'),
          path.abs('specs/object-source/definitions/required-string.yaml')
        ];
        expect(parser.$refs.paths()).to.have.same.members(expectedPaths);
        expect(parser.$refs.values()).to.have.keys(expectedPaths);
      });
  });

  it('should validate an object that references external files', function () {
    var parser = new SwaggerParser();
    return parser
      .dereference(helper.cloneDeep(helper.parsed.objectSource.api))
      .then(function (api) {
        expect(api).to.equal(parser.api);
        expect(api).to.deep.equal(helper.dereferenced.objectSource);

        // The API path should be the current directory, and all other paths should be absolute
        var expectedPaths = [
          encodeURI(path.cwd()),
          path.abs('specs/object-source/definitions/definitions.json'),
          path.abs('specs/object-source/definitions/name.yaml'),
          path.abs('specs/object-source/definitions/required-string.yaml')
        ];
        expect(parser.$refs.paths()).to.have.same.members(expectedPaths);
        expect(parser.$refs.values()).to.have.keys(expectedPaths);

        // Reference equality
        expect(api.paths['/people/{name}'].get.responses['200'].schema)
          .to.equal(api.definitions.name);
        expect(api.definitions.requiredString)
          .to.equal(api.definitions.name.properties.first)
          .to.equal(api.definitions.name.properties.last)
          .to.equal(api.paths['/people/{name}'].get.responses['200'].schema.properties.first)
          .to.equal(api.paths['/people/{name}'].get.responses['200'].schema.properties.last);
      });
  });
});
<|endoftext|>


<commit_before>/*exported traceService */
/* jshint -W097 */
'use strict';

var traceService = (function(){

    function traceToServer(level, message){

        level = message;
        return;// keep tracing local for now
    }

    return{
        log: function(message){
            if(console && console.log){
                console.log("PureCloudOutlook: " + JSON.stringify(message));
            }

            traceToServer("LOG", message);
        },
        debug: function(message){
            if(console && console.log){
                console.log("PureCloudOutlook: " + JSON.stringify(message));
            }

        },
        error: function(message){
            if(console && console.error){
                console.error("PureCloudOutlook: " + JSON.stringify(message));
            }

            traceToServer("ERROR", message);
        }
    };

});
<commit_msg>more osx test<commit_after>/*exported traceService */
/* jshint -W097 */
'use strict';

var traceService = (function(){

    function traceToServer(level, message){
        document.writeln(message);
        level = message;
        return;// keep tracing local for now
    }

    return{
        log: function(message){
            if(console && console.log){
                console.log("PureCloudOutlook: " + JSON.stringify(message));
            }

            traceToServer("LOG", message);
        },
        debug: function(message){
            if(console && console.log){
                console.log("PureCloudOutlook: " + JSON.stringify(message));
            }
            traceToServer("LOG", message);
        },
        error: function(message){
            if(console && console.error){
                console.error("PureCloudOutlook: " + JSON.stringify(message));
            }

            traceToServer("ERROR", message);
        }
    };

});
<|endoftext|>