<commit_before>import React from 'react';
import PropTypes from 'prop-types';
import Error from '../components/Error';
import withIntl from '../lib/withIntl';
import { graphql, compose } from 'react-apollo';
import gql from 'graphql-tag'
import { DropdownButton, MenuItem, Badge } from 'react-bootstrap';
import Currency from '../components/Currency';
import { FormattedMessage, defineMessages } from 'react-intl';
import ConnectPaypal from '../components/ConnectPaypal';
import AddFundsForm from '../components/AddFundsForm';
import { pick } from 'lodash';

class CollectivePickerWithData extends React.Component {

  static propTypes = {
    hostCollectiveSlug: PropTypes.string.isRequired,
    onChange: PropTypes.func
  }

  constructor(props) {
    super(props);
    this.state = {
      connectingPaypal: false,
      loading: false,
      showAddFunds: false
    };
    this.addFunds = this.addFunds.bind(this);
    this.toggleAddFunds = this.toggleAddFunds.bind(this);
    this.onChange = this.onChange.bind(this);
    this.messages = defineMessages({
      'badge.tooltip.pending': { id: 'expenses.badge.tooltip.pending', defaultMessage: "{pending} {pending, plural, one {expense} other {expenses}} pending approval" },
      'badge.tooltip.approved': { id: 'expenses.badge.tooltip.approved', defaultMessage: "{approved} {approved, plural, one {expense} other {expenses}} ready to be paid" }
    });
  }

  async addFunds(form) {
    if (form.totalAmount === 0) {
      return console.error("Total amount must be > 0");
    }
    this.setState({ loading: true });
    const hostCollective = this.hostCollective;
    const order = pick(form, ['totalAmount', 'description', 'hostFeePercent', 'platformFeePercent']);
    order.collective = {
      id: this.state.CollectiveId
    };
    if (form.email) {
      order.user = {
        email: form.email,
        name: form.name
      }
    } else if (form.organization) {
      order.fromCollective = {
        name: form.organization,
        website: form.website
      }
    } else {
      order.fromCollective = {
        id: form.FromCollectiveId || hostCollective.id
      }
    }
    const pm = hostCollective.paymentMethods.find(pm => pm.service === 'opencollective');
    if (!pm) {
      this.setState({ error: "This host doesn't have an opencollective payment method", loading: false });
      return console.error(">>> payment methods: ", hostCollective.paymentMethods);
    }
    order.paymentMethod = {
      uuid: pm.uuid
    }
    console.log(">>> add funds order: ", order);
    try {
      await this.props.createOrder(order);
      this.setState({ showAddFunds: false, loading: false });
    } catch (e) {
      const error = e.message && e.message.replace(/GraphQL error:/, "");
      this.setState({ error, loading: false });
    }
  }

  toggleAddFunds() {
    this.setState({ showAddFunds: !this.state.showAddFunds });
  }

  onChange(CollectiveId) {
    const collectives = this.hostCollective.collectives;
    const selectedCollective = CollectiveId > 0 && collectives.find(c => c.id === CollectiveId);
    this.setState({ CollectiveId });
    this.props.onChange(selectedCollective);
  }

  renderCollectiveMenuItem(collective, className) {
    const { intl } = this.props;
    const badgeCount = collective.stats.expenses.pending + collective.stats.expenses.approved;

    const tooltipArray = [];
    if (collective.stats.expenses.pending > 0) {
      tooltipArray.push(intl.formatMessage(this.messages['badge.tooltip.pending'], collective.stats.expenses));
    }
    if (collective.stats.expenses.approved > 0) {
      tooltipArray.push(intl.formatMessage(this.messages['badge.tooltip.approved'], collective.stats.expenses));
    }
    const tooltip = tooltipArray.join(', ') || '';

    return (<div className={`MenuItem-Collective ${className}`} title={tooltip}>

{collective.name}

          <FormattedMessage id="expenses.balance.label" defaultMessage="balance:" />
          <Currency value={collective.stats.balance} currency={collective.currency} />

      { badgeCount > 0 && <Badge pullRight={true}>{badgeCount}</Badge> }

);
  }

  render() {
    const { LoggedInUser, data: { loading, error, Collective } } = this.props;

    if (error) {
      console.error("graphql error>>>", error.message);
      return (<Error message="GraphQL error" />)
    }

    this.hostCollective = Collective || this.hostCollective;
    const canAddFunds = LoggedInUser && LoggedInUser.canEditCollective(this.hostCollective);

    if (loading || !this.hostCollective) {
      return (
);
    }

    const collectives = [...this.hostCollective.collectives].sort((a, b) => {
      return (b.name.toUpperCase()  c.id === this.state.CollectiveId);
    const selectedTitle = selectedCollective ? this.renderCollectiveMenuItem(selectedCollective, 'selected') :
<FormattedMessage id="expenses.allCollectives" defaultMessage="All Collectives" />
;

    return (

<FormattedMessage id="expenses.collectivePicker.title" defaultMessage="Finances" />

<FormattedMessage id="expenses.collectivePicker.subtitle" defaultMessage="for {n} {n, plural, one {collective} other {collectives}}" values={{n: collectives.length}} />

            { collectives.length > 0 &&

              <DropdownButton id="collectivePicker" bsStyle="default" title={selectedTitle} onSelect={this.onChange}>
                { this.state.CollectiveId &&
                <MenuItem key={null} eventKey={null}>
                  <FormattedMessage id="expenses.allCollectives" defaultMessage="All Collectives" />
                </MenuItem>
                  }
                { collectives.map(collective => (
                  <MenuItem key={collective.id} eventKey={collective.id} title={collective.name}>
                    { this.renderCollectiveMenuItem(collective) }
                  </MenuItem>
                  ))}
              </DropdownButton>
              { selectedCollective && !this.state.showAddFunds && canAddFunds &&
              <FormattedMessage id="addfunds.submit" defaultMessage="Add Funds" />
                }

            }

            { LoggedInUser && LoggedInUser.canEditCollective(this.hostCollective) &&
            <ConnectPaypal
              collective={this.hostCollective}
              />
              }

          { selectedCollective && this.state.showAddFunds &&

            <AddFundsForm
              collective={selectedCollective}
              host={this.hostCollective}
              onSubmit={this.addFunds}
              onCancel={this.toggleAddFunds}
              loading={this.state.loading}
              LoggedInUser={LoggedInUser}
              />

{this.state.error}

            }

    );
  }
}

const getCollectivesQuery = gql`
query Collective($hostCollectiveSlug: String!) {
  Collective(slug: $hostCollectiveSlug) {
    id
    slug
    name
    paymentMethods {
      id
      uuid
      service
      createdAt
      balance
      currency
    }
    collectives {
      id
      slug
      name
      currency
      hostFeePercent
      stats {
        id
        balance
        expenses {
          id
          all
          pending
          paid
          rejected
          approved
        }
      }
    }
  }
}
`;

const COLLECTIVES_PER_PAGE = 20;
export const addCollectivesData = graphql(getCollectivesQuery, {
  options(props) {
    return {
      variables: {
        hostCollectiveSlug: props.hostCollectiveSlug,
        offset: 0,
        limit: props.limit || COLLECTIVES_PER_PAGE * 2,
        includeHostedCollectives: true
      }
    }
  },
  props: ({ data }) => ({
    data,
    fetchMore: () => {
      return data.fetchMore({
        variables: {
          offset: data.allCollectives.length,
          limit: COLLECTIVES_PER_PAGE
        },
        updateQuery: (previousResult, { fetchMoreResult }) => {
          if (!fetchMoreResult) {
            return previousResult
          }
          return Object.assign({}, previousResult, {
            // Append the new posts results to the old one
            allCollectives: [...previousResult.allCollectives, ...fetchMoreResult.allCollectives]
          })
        }
      })
    }
  })
});

const createOrderQuery = gql`
mutation createOrder($order: OrderInputType!) {
  createOrder(order: $order) {
    id
    collective {
      id
      stats {
        id
        balance
      }
    }
  }
}
`;

const addMutation = graphql(createOrderQuery, {
props: ( { mutate }) => ({
  createOrder: async (order) => {
    return await mutate({ variables: { order } })
  }
})
});

const addGraphQL = compose(addMutation, addCollectivesData);

export default addGraphQL(withIntl(CollectivePickerWithData));
<commit_msg>feat(CollectivePickerData): Sort collectives on the server side<commit_after>import React from 'react';
import PropTypes from 'prop-types';
import Error from '../components/Error';
import withIntl from '../lib/withIntl';
import { graphql, compose } from 'react-apollo';
import gql from 'graphql-tag'
import { DropdownButton, MenuItem, Badge } from 'react-bootstrap';
import Currency from '../components/Currency';
import { FormattedMessage, defineMessages } from 'react-intl';
import ConnectPaypal from '../components/ConnectPaypal';
import AddFundsForm from '../components/AddFundsForm';
import { pick } from 'lodash';

class CollectivePickerWithData extends React.Component {

  static propTypes = {
    hostCollectiveSlug: PropTypes.string.isRequired,
    onChange: PropTypes.func
  }

  constructor(props) {
    super(props);
    this.state = {
      connectingPaypal: false,
      loading: false,
      showAddFunds: false
    };
    this.addFunds = this.addFunds.bind(this);
    this.toggleAddFunds = this.toggleAddFunds.bind(this);
    this.onChange = this.onChange.bind(this);
    this.messages = defineMessages({
      'badge.tooltip.pending': { id: 'expenses.badge.tooltip.pending', defaultMessage: "{pending} {pending, plural, one {expense} other {expenses}} pending approval" },
      'badge.tooltip.approved': { id: 'expenses.badge.tooltip.approved', defaultMessage: "{approved} {approved, plural, one {expense} other {expenses}} ready to be paid" }
    });
  }

  async addFunds(form) {
    if (form.totalAmount === 0) {
      return console.error("Total amount must be > 0");
    }
    this.setState({ loading: true });
    const hostCollective = this.hostCollective;
    const order = pick(form, ['totalAmount', 'description', 'hostFeePercent', 'platformFeePercent']);
    order.collective = {
      id: this.state.CollectiveId
    };
    if (form.email) {
      order.user = {
        email: form.email,
        name: form.name
      }
    } else if (form.organization) {
      order.fromCollective = {
        name: form.organization,
        website: form.website
      }
    } else {
      order.fromCollective = {
        id: form.FromCollectiveId || hostCollective.id
      }
    }
    const pm = hostCollective.paymentMethods.find(pm => pm.service === 'opencollective');
    if (!pm) {
      this.setState({ error: "This host doesn't have an opencollective payment method", loading: false });
      return console.error(">>> payment methods: ", hostCollective.paymentMethods);
    }
    order.paymentMethod = {
      uuid: pm.uuid
    }
    console.log(">>> add funds order: ", order);
    try {
      await this.props.createOrder(order);
      this.setState({ showAddFunds: false, loading: false });
    } catch (e) {
      const error = e.message && e.message.replace(/GraphQL error:/, "");
      this.setState({ error, loading: false });
    }
  }

  toggleAddFunds() {
    this.setState({ showAddFunds: !this.state.showAddFunds });
  }

  onChange(CollectiveId) {
    const collectives = this.hostCollective.collectives;
    const selectedCollective = CollectiveId > 0 && collectives.find(c => c.id === CollectiveId);
    this.setState({ CollectiveId });
    this.props.onChange(selectedCollective);
  }

  renderCollectiveMenuItem(collective, className) {
    const { intl } = this.props;
    const badgeCount = collective.stats.expenses.pending + collective.stats.expenses.approved;

    const tooltipArray = [];
    if (collective.stats.expenses.pending > 0) {
      tooltipArray.push(intl.formatMessage(this.messages['badge.tooltip.pending'], collective.stats.expenses));
    }
    if (collective.stats.expenses.approved > 0) {
      tooltipArray.push(intl.formatMessage(this.messages['badge.tooltip.approved'], collective.stats.expenses));
    }
    const tooltip = tooltipArray.join(', ') || '';

    return (<div className={`MenuItem-Collective ${className}`} title={tooltip}>

{collective.name}

          <FormattedMessage id="expenses.balance.label" defaultMessage="balance:" />
          <Currency value={collective.stats.balance} currency={collective.currency} />

      { badgeCount > 0 && <Badge pullRight={true}>{badgeCount}</Badge> }

);
  }

  render() {
    const { LoggedInUser, data: { loading, error, Collective } } = this.props;

    if (error) {
      console.error("graphql error>>>", error.message);
      return (<Error message="GraphQL error" />)
    }

    this.hostCollective = Collective || this.hostCollective;
    const canAddFunds = LoggedInUser && LoggedInUser.canEditCollective(this.hostCollective);

    if (loading || !this.hostCollective) {
      return (
);
    }

    const collectives = [...this.hostCollective.collectives];

    const selectedCollective = collectives.find(c => c.id === this.state.CollectiveId);
    const selectedTitle = selectedCollective ? this.renderCollectiveMenuItem(selectedCollective, 'selected') :
<FormattedMessage id="expenses.allCollectives" defaultMessage="All Collectives" />
;

    return (

<FormattedMessage id="expenses.collectivePicker.title" defaultMessage="Finances" />

<FormattedMessage id="expenses.collectivePicker.subtitle" defaultMessage="for {n} {n, plural, one {collective} other {collectives}}" values={{n: collectives.length}} />

            { collectives.length > 0 &&

              <DropdownButton id="collectivePicker" bsStyle="default" title={selectedTitle} onSelect={this.onChange}>
                { this.state.CollectiveId &&
                <MenuItem key={null} eventKey={null}>
                  <FormattedMessage id="expenses.allCollectives" defaultMessage="All Collectives" />
                </MenuItem>
                  }
                { collectives.map(collective => (
                  <MenuItem key={collective.id} eventKey={collective.id} title={collective.name}>
                    { this.renderCollectiveMenuItem(collective) }
                  </MenuItem>
                  ))}
              </DropdownButton>
              { selectedCollective && !this.state.showAddFunds && canAddFunds &&
              <FormattedMessage id="addfunds.submit" defaultMessage="Add Funds" />
                }

            }

            { LoggedInUser && LoggedInUser.canEditCollective(this.hostCollective) &&
            <ConnectPaypal
              collective={this.hostCollective}
              />
              }

          { selectedCollective && this.state.showAddFunds &&

            <AddFundsForm
              collective={selectedCollective}
              host={this.hostCollective}
              onSubmit={this.addFunds}
              onCancel={this.toggleAddFunds}
              loading={this.state.loading}
              LoggedInUser={LoggedInUser}
              />

{this.state.error}

            }

    );
  }
}

const getCollectivesQuery = gql`
query Collective($hostCollectiveSlug: String!, $orderBy: CollectiveOrderField, $orderDirection: OrderDirection) {
  Collective(slug: $hostCollectiveSlug) {
    id
    slug
    name
    paymentMethods {
      id
      uuid
      service
      createdAt
      balance
      currency
    }
    collectives(orderBy: $orderBy, orderDirection: $orderDirection) {
      id
      slug
      name
      currency
      hostFeePercent
      stats {
        id
        balance
        expenses {
          id
          all
          pending
          paid
          rejected
          approved
        }
      }
    }
  }
}
`;

const COLLECTIVES_PER_PAGE = 20;
export const addCollectivesData = graphql(getCollectivesQuery, {
  options(props) {
    return {
      variables: {
        hostCollectiveSlug: props.hostCollectiveSlug,
        offset: 0,
        limit: props.limit || COLLECTIVES_PER_PAGE * 2,
        includeHostedCollectives: true,
        orderBy: 'name',
        orderDirection: 'ASC',
      }
    }
  },
  props: ({ data }) => ({
    data,
    fetchMore: () => {
      return data.fetchMore({
        variables: {
          offset: data.allCollectives.length,
          limit: COLLECTIVES_PER_PAGE
        },
        updateQuery: (previousResult, { fetchMoreResult }) => {
          if (!fetchMoreResult) {
            return previousResult
          }
          return Object.assign({}, previousResult, {
            // Append the new posts results to the old one
            allCollectives: [...previousResult.allCollectives, ...fetchMoreResult.allCollectives]
          })
        }
      })
    }
  })
});

const createOrderQuery = gql`
mutation createOrder($order: OrderInputType!) {
  createOrder(order: $order) {
    id
    collective {
      id
      stats {
        id
        balance
      }
    }
  }
}
`;

const addMutation = graphql(createOrderQuery, {
props: ( { mutate }) => ({
  createOrder: async (order) => {
    return await mutate({ variables: { order } })
  }
})
});

const addGraphQL = compose(addMutation, addCollectivesData);

export default addGraphQL(withIntl(CollectivePickerWithData));
<|endoftext|>


<commit_before>!function(module, angular, undefined) {
  'use strict';

  angular.module('ngIntercom', ['angular-intercom']);

  module.value('IntercomSettings', {});

  module.provider('IntercomService', function() {
    var _asyncLoading = false;
    var _scriptUrl = '//static.intercomcdn.com/intercom.v1.js';

    this.asyncLoading = function(config) {
      _asyncLoading = config || _asyncLoading;
      return this;
    };

    this.scriptUrl = function(url) {
      _scriptUrl = url || _scriptUrl;
      return this;
    };

    // Create a script tag with moment as the source
    // and call our onScriptLoad callback when it
    // has been loaded
    function createScript($document, callback) {
      var scriptTag = $document.createElement('script');
      scriptTag.type = 'text/javascript';
      scriptTag.async = true;
      scriptTag.src = _scriptUrl;
      scriptTag.onreadystatechange = function () {
        if (this.readyState === 'complete') {
          callback();
        }
      };
      // Set the callback to be run
      // after the scriptTag has loaded
      scriptTag.onload = callback;
      // Attach the script tag to the document body
      var s = $document.getElementsByTagName('body')[0];
      s.appendChild(scriptTag);
    }

    this.$get = ['$document', '$timeout', '$q', '$window',
      function($document, $timeout, $q, $window) {
      var deferred = $q.defer();
      var _intercom = angular.isFunction($window.Intercom) ? $window.Intercom : angular.noop;

      if (_asyncLoading) {
        // Load client in the browser
        var onScriptLoad = function(callback) {
          $timeout(function() {
            // Resolve the deferred promise
            // as the Intercom object on the window
            deferred.resolve($window.Intercom);
          });
        };
        createScript($document[0], onScriptLoad);
      }

      return (_asyncLoading) ? deferred.promise: _intercom;
    }];
  });

  module.provider('Intercom', function() {

    this.$get = ['IntercomService', 'IntercomSettings', function(IntercomService, IntercomSettings) {
        var _options = {};

        angular.extend(_options, IntercomSettings);

        return {
          boot: function(options) {
            if (IntercomService.then) {
              IntercomService.then(function(intercom) {
                intercom('boot', options || _options);
              });
            } else {
              IntercomService('boot', options || _options);
            }
          },
          update: function(data) {
            if (IntercomService.then) {
              IntercomService.then(function(intercom) {
                if (data) {
                  intercom('update', data) ;
                } else {
                  intercom('update');
                }
              });
            } else {
              if (data) {
                IntercomService('update', data);
              } else {
                IntercomService('update');
              }
            }

          },
          shutdown: function() {
            if (IntercomService.then) {
              IntercomService.then(function(intercom) {
                intercom('shutdown');
              });
            } else {
              IntercomService('shutdown');
            }

          },
          hide: function() {
            if (IntercomService.then) {
              IntercomService.then(function(intercom) {
                intercom('hide');
              });
            } else {
              IntercomService('hide');
            }

          },
          show: function() {
            if (IntercomService.then) {
              IntercomService.then(function(intercom) {
                intercom('show');
              });
            } else {
              IntercomService('Show');
            }
          }
        }; // end return
    }]; // end $get
  });

}(angular.module('angular-intercom',[]), angular);
<commit_msg>Retry each 100ms for 1s intercom async loading, fixes #2<commit_after>!function(module, angular, undefined) {
  'use strict';

  angular.module('ngIntercom', ['angular-intercom']);

  module.value('IntercomSettings', {});

  module.provider('IntercomService', function() {
    var _asyncLoading = false;
    var _scriptUrl = '//static.intercomcdn.com/intercom.v1.js';

    this.asyncLoading = function(config) {
      _asyncLoading = config || _asyncLoading;
      return this;
    };

    this.scriptUrl = function(url) {
      _scriptUrl = url || _scriptUrl;
      return this;
    };

    // Create a script tag with moment as the source
    // and call our onScriptLoad callback when it
    // has been loaded
    function createScript($document, callback) {
      var scriptTag = $document.createElement('script');
      scriptTag.type = 'text/javascript';
      scriptTag.async = true;
      scriptTag.src = _scriptUrl;
      scriptTag.onreadystatechange = function () {
        if (this.readyState === 'complete') {
          callback();
        }
      };
      // Set the callback to be run
      // after the scriptTag has loaded
      scriptTag.onload = callback;
      // Attach the script tag to the document body
      var s = $document.getElementsByTagName('body')[0];
      s.appendChild(scriptTag);
    }

    this.$get = ['$document', '$timeout', '$q', '$window',
      function($document, $timeout, $q, $window) {
      var deferred = $q.defer();
      var _intercom = angular.isFunction($window.Intercom) ? $window.Intercom : angular.noop;

      if (_asyncLoading) {
        // wait up to 1 sec before aborting
        var _try = 10;
        // Load client in the browser
        var onScriptLoad = function tryF(callback) {
          $timeout(function() {
            if(_try === 0){
              return deferred.resolve($window.Intercom);
            }

            if($window.Intercom){
              // Resolve the deferred promise
              // as the Intercom object on the window
              return deferred.resolve($window.Intercom);
            }
            _try--;
            setTimeout(tryF.bind(null, callback), 100); // wait 100ms before next try
          });
        };
        createScript($document[0], onScriptLoad);
      }

      return (_asyncLoading) ? deferred.promise: _intercom;
    }];
  });

  module.provider('Intercom', function() {

    this.$get = ['IntercomService', 'IntercomSettings', function(IntercomService, IntercomSettings) {
        var _options = {};

        angular.extend(_options, IntercomSettings);

        return {
          boot: function(options) {
            if (IntercomService.then) {
              IntercomService.then(function(intercom) {
                intercom('boot', options || _options);
              });
            } else {
              IntercomService('boot', options || _options);
            }
          },
          update: function(data) {
            if (IntercomService.then) {
              IntercomService.then(function(intercom) {
                if (data) {
                  intercom('update', data) ;
                } else {
                  intercom('update');
                }
              });
            } else {
              if (data) {
                IntercomService('update', data);
              } else {
                IntercomService('update');
              }
            }

          },
          shutdown: function() {
            if (IntercomService.then) {
              IntercomService.then(function(intercom) {
                intercom('shutdown');
              });
            } else {
              IntercomService('shutdown');
            }

          },
          hide: function() {
            if (IntercomService.then) {
              IntercomService.then(function(intercom) {
                intercom('hide');
              });
            } else {
              IntercomService('hide');
            }

          },
          show: function() {
            if (IntercomService.then) {
              IntercomService.then(function(intercom) {
                intercom('show');
              });
            } else {
              IntercomService('Show');
            }
          }
        }; // end return
    }]; // end $get
  });

}(angular.module('angular-intercom',[]), angular);
<|endoftext|>


<commit_before>import React from 'react'
import Simulator from './simulator'

class EventListenerSimulator extends React.Component {
  constructor (props) {
    super(props)

    this.state = {
      eventName: props.eventName,
      selectedBets: []
    }
    this.handleOnSelectedBetsCleared = this.handleOnSelectedBetsCleared.bind(this)
  }

  componentDidMount () {
    if (this.state.eventName !== null) {
      window.addEventListener(this.state.eventName, ({ detail }) =>
        this.setState({
          selectedBets: this.state.selectedBets.concat({
            code: detail.event.code,
            home: detail.event.home,
            away: detail.event.away,
            name: detail.betType,
            odd: detail.odd
          })
        })
      )
    }
  }

  componentWillUnmount () {
    if (this.state.eventName !== null) {
      window.removeEventListener(this.state.eventName)
    }
  }

  handleOnSelectedBetsCleared () {
    this.setState({
      selectedBets: []
    })
  }

  render () {
    return (
      <Simulator
        selectedBets={this.state.selectedBets}
        onSelectedBetsCleared={this.handleOnSelectedBetsCleared}
      />
    )
  }
}

EventListenerSimulator.defaultProps = {
  eventName: null
}

export default EventListenerSimulator
<commit_msg>Pass function to simulator component to remove a certain bet from the seleced bets array;<commit_after>import React from 'react'
import Simulator from './simulator'

class EventListenerSimulator extends React.Component {
  constructor (props) {
    super(props)

    this.state = {
      eventName: props.eventName,
      selectedBets: []
    }
    this.handleOnSelectedBetsCleared = this.handleOnSelectedBetsCleared.bind(this)
    this.handleOnSelectedBetRemoved = this.handleOnSelectedBetRemoved.bind(this)
  }

  componentDidMount () {
    if (this.state.eventName !== null) {
      window.addEventListener(this.state.eventName, ({ detail }) =>
        this.setState({
          selectedBets: this.state.selectedBets.concat({
            code: detail.event.code,
            home: detail.event.home,
            away: detail.event.away,
            name: detail.betType,
            odd: detail.odd
          })
        })
      )
    }
  }

  componentWillUnmount () {
    if (this.state.eventName !== null) {
      window.removeEventListener(this.state.eventName)
    }
  }

  handleOnSelectedBetsCleared () {
    this.setState({
      selectedBets: []
    })
  }

  handleOnSelectedBetRemoved (betToRemove) {
    const filteredSelectedBets = this.state.selectedBets.filter(
      bet => bet.code !== betToRemove.code
    )

    if (filteredSelectedBets.length < this.state.selectedBets.length) {
      this.setState({
        selectedBets: filteredSelectedBets
      })
    }
  }

  render () {
    return (
      <Simulator
        selectedBets={this.state.selectedBets}
        onSelectedBetsCleared={this.handleOnSelectedBetsCleared}
        onSelectedBetRemoved={this.handleOnSelectedBetRemoved}
      />
    )
  }
}

EventListenerSimulator.defaultProps = {
  eventName: null
}

export default EventListenerSimulator
<|endoftext|>


<commit_before>'use strict';

var join = require( 'path' ).join;
var writeFile = require( 'fs' ).writeFileSync;
var mkdirp = require( 'mkdirp' ).sync;
var collapse = require( 'bundle-collapser/plugin' );
var uglifyify = require( 'uglifyify' );
var pkgNames = require( '@stdlib/_tools/pkgs/names' );
var bundle = require( './../../lib' );

var fopts1 = {
	'pattern': '**/package.json',
	'ignore': [
		'**/_**/**',     // ignore "private" packages
		'**/datasets/**' // ignore dataset packages
	]
};

var fopts2 = {
	'pattern': '**/datasets/**/package.json', // only dataset packages
	'ignore': [
		'**/_**/**' // ignore "private" packages
	]
};

var uopts = {
	'global': true
};

var bopts1 = {
	'namespace': 'flat',
	'exportName': '@stdlib',
	'transforms': [
		[ uglifyify, uopts ] // minify modules individually
	],
	'plugins': [
		collapse // convert bundle paths to IDs
	],
	'external': [
		'@stdlib/datasets' // partial file path used to match omitted files
	]
};

var bopts2 = {
	'namespace': 'flat',
	'exportName': '@stdlib/datasets',
	'transforms': [
		[ uglifyify, uopts ] // minify modules individually
	],
	'plugins': [
		collapse // convert bundle paths to IDs
	]
};

var dir = join( __dirname, 'build' );
mkdirp( dir );

pkgNames( fopts1, onNames1 );
pkgNames( fopts2, onNames2 );

function onNames1( error, names ) {
	if ( error ) {
		throw error;
	}
	bundle( names, bopts1, onBundle1 );
}

function onNames2( error, names ) {
	if ( error ) {
		throw error;
	}
	bundle( names, bopts2, onBundle2 );
}

function onBundle1( error, bundle ) {
	var fpath;
	if ( error ) {
		throw error;
	}
	fpath = join( dir, 'bundle.min.js' );
	writeFile( fpath, bundle );
}

function onBundle2( error, bundle ) {
	var fpath;
	if ( error ) {
		throw error;
	}
	fpath = join( dir, 'datasets.min.js' );
	writeFile( fpath, bundle );
}
<commit_msg>Refactor example using synchronous methods<commit_after>'use strict';

var join = require( 'path' ).join;
var writeFile = require( 'fs' ).writeFileSync;
var mkdirp = require( 'mkdirp' ).sync;
var collapse = require( 'bundle-collapser/plugin' );
var uglifyify = require( 'uglifyify' );
var pkgNames = require( '@stdlib/_tools/pkgs/names' ).sync;
var instanceOf = require( '@stdlib/assert/instance-of' );
var bundle = require( './../../lib' );

// Define package resolution options:
var fopts1 = {
	'pattern': '**/package.json',
	'ignore': [
		'**/_**/**',     // ignore "private" packages
		'**/datasets/**' // ignore dataset packages
	]
};

var fopts2 = {
	'pattern': '**/datasets/**/package.json', // only dataset packages
	'ignore': [
		'**/_**/**'      // ignore "private" packages
	]
};

// Resolve packages:
var names1 = pkgNames( fopts1 );
if ( instanceOf( names1, Error ) ) {
	throw names1;
}
var names2 = pkgNames( fopts2 );
if ( instanceOf( names2, Error ) ) {
	throw names2;
}

// Create an output build directory:
var dir = join( __dirname, 'build' );
mkdirp( dir );

// Define bundle options:
var uopts = {
	'global': true
};

var bopts1 = {
	'namespace': 'flat',
	'exportName': '@stdlib',
	'transforms': [
		[ uglifyify, uopts ] // minify modules individually
	],
	'plugins': [
		collapse             // convert bundle paths to IDs
	],
	'external': names2       // omit datasets package from the main bundle
};

var bopts2 = {
	'namespace': 'flat',
	'exportName': '@stdlib/datasets',
	'transforms': [
		[ uglifyify, uopts ] // minify modules individually
	],
	'plugins': [
		collapse             // convert bundle paths to IDs
	]
};

// Generate bundles:
bundle( names1, bopts1, onBundle1 );
bundle( names2, bopts2, onBundle2 );

function onBundle1( error, bundle ) {
	var fpath;
	if ( error ) {
		throw error;
	}
	fpath = join( dir, 'bundle.min.js' );
	writeFile( fpath, bundle );
}

function onBundle2( error, bundle ) {
	var fpath;
	if ( error ) {
		throw error;
	}
	fpath = join( dir, 'datasets.min.js' );
	writeFile( fpath, bundle );
}
<|endoftext|>


<commit_before>(function(vc){
    //var _fileUrl = 'https://hc.demo.winqi.cn/callComponent/download/getFile/fileByObjId';
    var _fileUrl = '/callComponent/download/getFile/fileByObjId';
    vc.extends({
        propTypes: {
            notifyLoadDataComponentName:vc.propTypes.string
        },
        data:{
            editOwnerInfo:{
                ownerId:'',
                memberId:'',
                name:'',
                age:'',
                link:'',
                sex:'',
                remark:'',
                ownerPhoto:'',
                idCard:'',
                videoPlaying:false
            }
        },
         _initMethod:function(){

         },
         _initEvent:function(){
            vc.on('editOwner','openEditOwnerModal',function(_owner){
                vc.copyObject(_owner,vc.component.editOwnerInfo);
                //根据memberId 查询 照片信息
                vc.component.editOwnerInfo.ownerPhoto = _fileUrl+"?objId="+
                   vc.component.editOwnerInfo.memberId +"&communityId="+vc.getCurrentCommunity().communityId+"&fileTypeCd=10000&time="+new Date();
                $('#editOwnerModel').modal('show');
                vc.component._initAddOwnerMediaForEdit();
            });
        },
        methods:{
            editOwnerValidate:function(){
                return vc.validate.validate({
                    editOwnerInfo:vc.component.editOwnerInfo
                },{
                   'editOwnerInfo.name':[
                        {
                            limit:"required",
                            param:"",
                            errInfo:"名称不能为空"
                        },
                        {
                            limit:"maxin",
                            param:"2,10",
                            errInfo:"名称长度必须在2位至10位"
                        },
                    ],
                    'editOwnerInfo.age':[
                        {
                            limit:"required",
                            param:"",
                            errInfo:"年龄不能为空"
                        },
                        {
                            limit:"num",
                            param:"",
                            errInfo:"年龄不是有效的数字"
                        },
                    ],
                    'editOwnerInfo.sex':[
                        {
                            limit:"required",
                            param:"",
                            errInfo:"性别不能为空"
                        }
                    ],
                    'editOwnerInfo.idCard':[
                        {
                            limit:"required",
                            param:"",
                            errInfo:"身份证号不能为空"
                        },
                        {
                            limit:"idCard",
                            param:"",
                            errInfo:"不是有效的身份证号"
                        }
                    ],
                    'editOwnerInfo.link':[
                        {
                            limit:"required",
                            param:"",
                            errInfo:"手机号不能为空"
                        },
                        {
                            limit:"phone",
                            param:"",
                            errInfo:"不是有效的手机号"
                        }
                    ],
                    'editOwnerInfo.remark':[

                        {
                            limit:"maxLength",
                            param:"200",
                            errInfo:"备注长度不能超过200位"
                        }
                    ]

                });
            },

            editOwnerMethod:function(){

                if(!vc.component.editOwnerValidate()){
                    vc.message(vc.validate.errInfo);

                    return ;
                }

                vc.component.editOwnerInfo.communityId = vc.getCurrentCommunity().communityId;

                //编辑时 ownerPhoto 中内容不是照片内容，则清空
                if(vc.component.editOwnerInfo.ownerPhoto.indexOf(_fileUrl) != -1){
                    vc.component.editOwnerInfo.ownerPhoto = "";
                }
                vc.http.post(
                    'editOwner',
                    'changeOwner',
                    JSON.stringify(vc.component.editOwnerInfo),
                    {
                        emulateJSON:true
                     },
                     function(json,res){
                        //vm.menus = vm.refreshMenuActive(JSON.parse(json),0);
                        if(res.status == 200){
                            //关闭model
                            $('#editOwnerModel').modal('hide');
                            vc.component.clearEditOwnerInfo();
                            vc.emit($props.notifyLoadDataComponentName,'listOwnerData',{});

                            return ;
                        }
                        vc.message(json);

                     },
                     function(errInfo,error){
                        console.log('请求失败处理');
                        vc.message(errInfo);
                     });
            },
            clearEditOwnerInfo:function(){
                vc.component.editOwnerInfo = {
                    ownerId:'',
                    memberId:'',
                    name:'',
                    age:'',
                    link:'',
                    sex:'',
                    remark:'',
                    ownerPhoto:'',
                    videoPlaying:false
                };
            },
            _editUserMedia:function() {
                return navigator.getUserMedia = navigator.getUserMedia ||
                    navigator.webkitGetUserMedia ||
                    navigator.mozGetUserMedia ||
                    navigator.msGetUserMedia || null;
            },
            _initAddOwnerMediaForEdit:function () {
                if(vc.component._editUserMedia()){
                    vc.component.editOwnerInfo.videoPlaying = false;
                    var constraints = {
                        video: true,
                        audio: false
                    };
                    var video = document.getElementById('ownerPhotoForEdit');
                    var media = navigator.getUserMedia(constraints, function (stream) {
                        var url = window.URL || window.webkitURL;
                        //video.src = url ? url.createObjectURL(stream) : stream;
                        try {
                            video.src = url ? url.createObjectURL(stream) : stream;
                        } catch (error) {
                            video.srcObject = stream;
                        }
                        video.play();
                        vc.component.editOwnerInfo.videoPlaying = true;
                    }, function (error) {
                        console.log("ERROR");
                        console.log(error);
                    });
                }else{
                    console.log("初始化视频失败");
                }
            },
            _takePhotoForEdit:function () {
                if (vc.component.editOwnerInfo.videoPlaying) {
                    var canvas = document.getElementById('canvasForEdit');
                    var video = document.getElementById('ownerPhotoForEdit');
                    canvas.width = video.videoWidth;
                    canvas.height = video.videoHeight;
                    canvas.getContext('2d').drawImage(video, 0, 0);
                    var data = canvas.toDataURL('image/webp');
                    vc.component.editOwnerInfo.ownerPhoto = data;
                    //document.getElementById('photo').setAttribute('src', data);
                }
            },
            uploadEditPhoto:function(event){
                $("#uploadEditOwnerPhoto").trigger("click")
            },
            _chooseEditPhoto:function(event){
                var photoFiles = event.target.files;
                if (photoFiles && photoFiles.length > 0) {
                    // 获取目前上传的文件
                    var file = photoFiles[0];// 文件大小校验的动作
                    if(file.size > 1024 * 1024 * 1) {
                        vc.toast("图片大小不能超过 2MB!")
                        return false;
                    }
                    var reader = new FileReader(); //新建FileReader对象
                    reader.readAsDataURL(file); //读取为base64
                    reader.onloadend = function(e) {
                        vc.component.editOwnerInfo.ownerPhoto = reader.result;
                    }
                }
            },
        }
    });

})(window.vc);<commit_msg>报错 _uploadEditPhoto is not defined<commit_after>(function(vc){
    //var _fileUrl = 'https://hc.demo.winqi.cn/callComponent/download/getFile/fileByObjId';
    var _fileUrl = '/callComponent/download/getFile/fileByObjId';
    vc.extends({
        propTypes: {
            notifyLoadDataComponentName:vc.propTypes.string
        },
        data:{
            editOwnerInfo:{
                ownerId:'',
                memberId:'',
                name:'',
                age:'',
                link:'',
                sex:'',
                remark:'',
                ownerPhoto:'',
                idCard:'',
                videoPlaying:false
            }
        },
         _initMethod:function(){

         },
         _initEvent:function(){
            vc.on('editOwner','openEditOwnerModal',function(_owner){
                vc.copyObject(_owner,vc.component.editOwnerInfo);
                //根据memberId 查询 照片信息
                vc.component.editOwnerInfo.ownerPhoto = _fileUrl+"?objId="+
                   vc.component.editOwnerInfo.memberId +"&communityId="+vc.getCurrentCommunity().communityId+"&fileTypeCd=10000&time="+new Date();
                $('#editOwnerModel').modal('show');
                vc.component._initAddOwnerMediaForEdit();
            });
        },
        methods:{
            editOwnerValidate:function(){
                return vc.validate.validate({
                    editOwnerInfo:vc.component.editOwnerInfo
                },{
                   'editOwnerInfo.name':[
                        {
                            limit:"required",
                            param:"",
                            errInfo:"名称不能为空"
                        },
                        {
                            limit:"maxin",
                            param:"2,10",
                            errInfo:"名称长度必须在2位至10位"
                        },
                    ],
                    'editOwnerInfo.age':[
                        {
                            limit:"required",
                            param:"",
                            errInfo:"年龄不能为空"
                        },
                        {
                            limit:"num",
                            param:"",
                            errInfo:"年龄不是有效的数字"
                        },
                    ],
                    'editOwnerInfo.sex':[
                        {
                            limit:"required",
                            param:"",
                            errInfo:"性别不能为空"
                        }
                    ],
                    'editOwnerInfo.idCard':[
                        {
                            limit:"required",
                            param:"",
                            errInfo:"身份证号不能为空"
                        },
                        {
                            limit:"idCard",
                            param:"",
                            errInfo:"不是有效的身份证号"
                        }
                    ],
                    'editOwnerInfo.link':[
                        {
                            limit:"required",
                            param:"",
                            errInfo:"手机号不能为空"
                        },
                        {
                            limit:"phone",
                            param:"",
                            errInfo:"不是有效的手机号"
                        }
                    ],
                    'editOwnerInfo.remark':[

                        {
                            limit:"maxLength",
                            param:"200",
                            errInfo:"备注长度不能超过200位"
                        }
                    ]

                });
            },

            editOwnerMethod:function(){

                if(!vc.component.editOwnerValidate()){
                    vc.message(vc.validate.errInfo);

                    return ;
                }

                vc.component.editOwnerInfo.communityId = vc.getCurrentCommunity().communityId;

                //编辑时 ownerPhoto 中内容不是照片内容，则清空
                if(vc.component.editOwnerInfo.ownerPhoto.indexOf(_fileUrl) != -1){
                    vc.component.editOwnerInfo.ownerPhoto = "";
                }
                vc.http.post(
                    'editOwner',
                    'changeOwner',
                    JSON.stringify(vc.component.editOwnerInfo),
                    {
                        emulateJSON:true
                     },
                     function(json,res){
                        //vm.menus = vm.refreshMenuActive(JSON.parse(json),0);
                        if(res.status == 200){
                            //关闭model
                            $('#editOwnerModel').modal('hide');
                            vc.component.clearEditOwnerInfo();
                            vc.emit($props.notifyLoadDataComponentName,'listOwnerData',{});

                            return ;
                        }
                        vc.message(json);

                     },
                     function(errInfo,error){
                        console.log('请求失败处理');
                        vc.message(errInfo);
                     });
            },
            clearEditOwnerInfo:function(){
                vc.component.editOwnerInfo = {
                    ownerId:'',
                    memberId:'',
                    name:'',
                    age:'',
                    link:'',
                    sex:'',
                    remark:'',
                    ownerPhoto:'',
                    videoPlaying:false
                };
            },
            _editUserMedia:function() {
                return navigator.getUserMedia = navigator.getUserMedia ||
                    navigator.webkitGetUserMedia ||
                    navigator.mozGetUserMedia ||
                    navigator.msGetUserMedia || null;
            },
            _initAddOwnerMediaForEdit:function () {
                if(vc.component._editUserMedia()){
                    vc.component.editOwnerInfo.videoPlaying = false;
                    var constraints = {
                        video: true,
                        audio: false
                    };
                    var video = document.getElementById('ownerPhotoForEdit');
                    var media = navigator.getUserMedia(constraints, function (stream) {
                        var url = window.URL || window.webkitURL;
                        //video.src = url ? url.createObjectURL(stream) : stream;
                        try {
                            video.src = url ? url.createObjectURL(stream) : stream;
                        } catch (error) {
                            video.srcObject = stream;
                        }
                        video.play();
                        vc.component.editOwnerInfo.videoPlaying = true;
                    }, function (error) {
                        console.log("ERROR");
                        console.log(error);
                    });
                }else{
                    console.log("初始化视频失败");
                }
            },
            _takePhotoForEdit:function () {
                if (vc.component.editOwnerInfo.videoPlaying) {
                    var canvas = document.getElementById('canvasForEdit');
                    var video = document.getElementById('ownerPhotoForEdit');
                    canvas.width = video.videoWidth;
                    canvas.height = video.videoHeight;
                    canvas.getContext('2d').drawImage(video, 0, 0);
                    var data = canvas.toDataURL('image/webp');
                    vc.component.editOwnerInfo.ownerPhoto = data;
                    //document.getElementById('photo').setAttribute('src', data);
                }
            },
            _uploadEditPhoto:function(event){
                $("#uploadEditOwnerPhoto").trigger("click")
            },
            _chooseEditPhoto:function(event){
                var photoFiles = event.target.files;
                if (photoFiles && photoFiles.length > 0) {
                    // 获取目前上传的文件
                    var file = photoFiles[0];// 文件大小校验的动作
                    if(file.size > 1024 * 1024 * 1) {
                        vc.toast("图片大小不能超过 2MB!")
                        return false;
                    }
                    var reader = new FileReader(); //新建FileReader对象
                    reader.readAsDataURL(file); //读取为base64
                    reader.onloadend = function(e) {
                        vc.component.editOwnerInfo.ownerPhoto = reader.result;
                    }
                }
            },
        }
    });

})(window.vc);<|endoftext|>


<commit_before>/* eslint-disable no-param-reassign */

describe('the prime numbers canary spec', () => {
  it('shows the infrastructure works', () => {
    true.should.be.true();
  });

  const primeFactorsOf = (number) => {
    const factors = [];
    for (number > 1; number % 2 === 0; number /= 2) factors.push(2);
    if (number > 1) factors.push(number);

    return factors;
  };

  describe('a prime numbers function should', () => {
    it('return none for 1', () => {
      primeFactorsOf(1).should.deepEqual([]);
    });

    it('return 2 for 2', () => {
      primeFactorsOf(2).should.deepEqual([2]);
    });

    it('return 3 for 3', () => {
      primeFactorsOf(3).should.deepEqual([3]);
    });

    it('return 2, 2 for 4', () => {
      primeFactorsOf(4).should.deepEqual([2, 2]);
    });

    it('return 5 for 5', () => {
      primeFactorsOf(5).should.deepEqual([5]);
    });

    it('return 2, 3 for 6', () => {
      primeFactorsOf(6).should.deepEqual([2, 3]);
    });

    it('return 7 for 7', () => {
      primeFactorsOf(7).should.deepEqual([7]);
    });

    it('return 2, 2, 2 for 8', () => {
      primeFactorsOf(8).should.deepEqual([2, 2, 2]);
    });

    it('return 3, 3 for 9', () => {
      primeFactorsOf(9).should.deepEqual([3, 3]);
    });
  });
});
<commit_msg>(1) - pass the tests<commit_after>/* eslint-disable no-param-reassign */

describe('the prime numbers canary spec', () => {
  it('shows the infrastructure works', () => {
    true.should.be.true();
  });

  const primeFactorsOf = (number) => {
    const factors = [];

    for (number > 1; number % 2 === 0; number /= 2) factors.push(2);
    for (number > 1; number % 3 === 0; number /= 3) factors.push(3);
    if (number > 1) factors.push(number);

    return factors;
  };

  describe('a prime numbers function should', () => {
    it('return none for 1', () => {
      primeFactorsOf(1).should.deepEqual([]);
    });

    it('return 2 for 2', () => {
      primeFactorsOf(2).should.deepEqual([2]);
    });

    it('return 3 for 3', () => {
      primeFactorsOf(3).should.deepEqual([3]);
    });

    it('return 2, 2 for 4', () => {
      primeFactorsOf(4).should.deepEqual([2, 2]);
    });

    it('return 5 for 5', () => {
      primeFactorsOf(5).should.deepEqual([5]);
    });

    it('return 2, 3 for 6', () => {
      primeFactorsOf(6).should.deepEqual([2, 3]);
    });

    it('return 7 for 7', () => {
      primeFactorsOf(7).should.deepEqual([7]);
    });

    it('return 2, 2, 2 for 8', () => {
      primeFactorsOf(8).should.deepEqual([2, 2, 2]);
    });

    it('return 3, 3 for 9', () => {
      primeFactorsOf(9).should.deepEqual([3, 3]);
    });
  });
});
<|endoftext|>


<commit_before>/*---------------------------------------------------------------------------
  Copyright 2013 Microsoft Corporation.

  This is free software; you can redistribute it and/or modify it under the
  terms of the Apache License, Version 2.0. A copy of the License can be
  found in the file "license.txt" at the root of this distribution.
---------------------------------------------------------------------------*/

// Provide client/server storage
// This module provides file access operations. On the web client, these
// operations only provide accesss to a global object of files which is
// *not* persistent. This code is mainly to ensure we can share as much
// code as possible between client and server.
var onServer = ($std_core.getHost() === "nodejs");

var $readFileSync;
var $writeFileSync;
var $renameSync;
var $fexistsSync;
var $relative;
var $mkdirp;
var $cwd;
var $clear;
var $unlinkSync;
var vfs = {};

if (onServer) {
  var fs = require("fs");
  var path = require("path");
  var xmkdirp = require('mkdirp');

  $readFileSync = function(fname,enc) { return fs.readFileSync(fname,{encoding:enc}); };
  $writeFileSync = function(fname,enc,data) { return fs.writeFileSync(fname,data,{encoding:enc}); };
  $fexistsSync = function(fname) { return (fs.existsSync(fname) != 0);};
  $relative = function(dir,p) { return path.relative(dir,p); };
  $cwd = function() { return process.cwd(); };
  $mkdirp = function(dir,mode) { return xmkdirp.sync(dir,mode); };
  $renameSync = function(oldname,newname) { return fs.renameSync(oldname,newname); };
  $clear = function() { };
  $unlinkSync = function(fname) { return fs.unlinkSync(fname); };
}
else {
  $readFileSync = function(fname,enc) {
    var data = vfs["/" + fname];
    if (data === undefined) throw ("Could not read: " + fname);
    return data;
  }

  $writeFileSync = function(fname,enc,data) {
    vfs["/" + fname] = data;
  }

  $fexistsSync = function(fname) {
    return (vfs["/" + fname] !== undefined);
  }

  $relative = function(dir,p) {
    return p; // TODO: implement this client side.
  }

  $cwd = function() {
    return "."; // ??
  }

  $mkdirp = function(dir,mode) {
    // do nothing
  }

  $renameSync = function(oldname,newname) {
    $writeFileSync( newname, $readFileSync(oldname) );
  }

  $clear = function() {
    vfs = {};
  }

  $unlinkSync = function(fname) {
    var data = vfs["/" + fname];
    if (data != null) {
      delete vfs["/" + fname];
    }
    return null;
  }
}
<commit_msg>Fixed bug in file rename function that would leave the new file empty!<commit_after>/*---------------------------------------------------------------------------
  Copyright 2013 Microsoft Corporation.

  This is free software; you can redistribute it and/or modify it under the
  terms of the Apache License, Version 2.0. A copy of the License can be
  found in the file "license.txt" at the root of this distribution.
---------------------------------------------------------------------------*/

// Provide client/server storage
// This module provides file access operations. On the web client, these
// operations only provide accesss to a global object of files which is
// *not* persistent. This code is mainly to ensure we can share as much
// code as possible between client and server.
var onServer = ($std_core.getHost() === "nodejs");

var $readFileSync;
var $writeFileSync;
var $renameSync;
var $fexistsSync;
var $relative;
var $mkdirp;
var $cwd;
var $clear;
var $unlinkSync;
var vfs = {};

if (onServer) {
  var fs = require("fs");
  var path = require("path");
  var xmkdirp = require('mkdirp');

  $readFileSync = function(fname,enc) { return fs.readFileSync(fname,{encoding:enc}); };
  $writeFileSync = function(fname,enc,data) { return fs.writeFileSync(fname,data,{encoding:enc}); };
  $fexistsSync = function(fname) { return (fs.existsSync(fname) != 0);};
  $relative = function(dir,p) { return path.relative(dir,p); };
  $cwd = function() { return process.cwd(); };
  $mkdirp = function(dir,mode) { return xmkdirp.sync(dir,mode); };
  $renameSync = function(oldname,newname) { return fs.renameSync(oldname,newname); };
  $clear = function() { };
  $unlinkSync = function(fname) { return fs.unlinkSync(fname); };
}
else {
  $readFileSync = function(fname,enc) {
    var data = vfs["/" + fname];
    if (data === undefined) throw ("Could not read: " + fname);
    return data;
  }

  $writeFileSync = function(fname,enc,data) {
    vfs["/" + fname] = data;
  }

  $fexistsSync = function(fname) {
    return (vfs["/" + fname] !== undefined);
  }

  $relative = function(dir,p) {
    return p; // TODO: implement this client side.
  }

  $cwd = function() {
    return "."; // ??
  }

  $mkdirp = function(dir,mode) {
    // do nothing
  }

  $renameSync = function(oldname,newname) {
    $writeFileSync( newname, "binary", $readFileSync(oldname) );
  }

  $clear = function() {
    vfs = {};
  }

  $unlinkSync = function(fname) {
    var data = vfs["/" + fname];
    if (data != null) {
      delete vfs["/" + fname];
    }
    return null;
  }
}
<|endoftext|>


<commit_before>'use strict';

/*
* The original C++ code and copyright notice is from the [Boost library]{@link http://www.boost.org/doc/libs/1_62_0/boost/math/special_functions/beta.hpp}.
*
* The implementation has been modified for JavaScript.
*/

/*
* (C) Copyright John Maddock 2006.
* Use, modification and distribution are subject to the
* Boost Software License, Version 1.0. (See accompanying file
* LICENSE or copy at http://www.boost.org/LICENSE_1_0.txt)
*/

// MODULES //

var lanczosSumExpGScaled = require( '@stdlib/math/base/special/gamma-lanczos-sum-expg-scaled' );
var expm1 = require( '@stdlib/math/base/special/expm1' );
var log1p = require( '@stdlib/math/base/special/log1p' );
var sqrt = require( '@stdlib/math/base/special/sqrt' );
var abs = require( '@stdlib/math/base/special/abs' );
var exp = require( '@stdlib/math/base/special/exp' );
var pow = require( '@stdlib/math/base/special/pow' );
var max = require( '@stdlib/math/base/special/max' );
var min = require( '@stdlib/math/base/special/min' );
var ln = require( '@stdlib/math/base/special/ln' );
var MAX_LN = require( '@stdlib/math/constants/float64-max-ln' );
var MIN_LN = require( '@stdlib/math/constants/float64-min-ln' );
var G = require( '@stdlib/math/constants/float64-gamma-lanczos-g' );
var E = require( '@stdlib/math/constants/float64-e' );

// MAIN //

/**
* Computes the leading power terms in the incomplete beta function. When normalized,
*
* ```tex
* \frac{ x^a y^b }{ \operatorname{Beta}(a,b) }
* ```
*
* and otherwise
*
* ```tex
* x^a y^b
* ```
*
* #### Notes
*
* - Almost all of the error in the incomplete beta comes from this function, particularly when \\( a \\) and \\( b \\) are large. Computing large powers are *hard* though, and using logarithms just leads to horrendous cancellation errors.
* - For \\( l1 * l2 > 0 \\) or \\( \operatorname{min}( a, b ) < 1 \\), the two power terms both go in the same direction (toward zero or toward infinity). In this case if either term overflows or underflows, then the product of the two must do so also. Alternatively, if one exponent is less than one, then we can't productively use it to eliminate overflow or underflow from the other term.  Problems with spurious overflow/underflow can't be ruled out. In this case, but it is *very* unlikely since one of the power terms will evaluate to a number close to 1.
* - If \\( \max( \abs(l1), \abs(l2) ) < 0.5 \\), both exponents are near one and both the exponents are greater than one, and, further, these two power terms tend in opposite directions (one toward zero, the other toward infinity), so we have to combine the terms to avoid any risk of overflow or underflow. We do this by moving one power term inside the other, we have:
*
*    ```tex
*    (1 + l_1)^a \cdot (1 + l_2)^b \\
*    = ((1 + l_1) \cdot (1 + l_2)^(b/a))^a \\
*    = (1 + l_1 + l_3 + l_1*l_3)^a
*    ```
*
*    and
*
*    ```tex
*    l_3 = (1 + l_2)^(b/a) - 1 \\
*    = \exp((b/a) * \ln(1 + l_2)) - 1
*    ```
*
*    The tricky bit is deciding which term to move inside. By preference, we move the larger term inside, so that the size of the largest exponent is reduced.  However, that can only be done as long as l3 (see above) is also small.
*
* @private
* @param {NonNegativeNumber} a - function parameter
* @param {NonNegativeNumber} b - function parameter
* @param {Probability} x - function parameter
* @param {Probability} y - probability equal to `1-x`
* @param {boolean} normalized - boolean indicating whether to evaluate the power terms of the regularized or non-regularized incomplete beta function
* @returns {number} power terms
*/
function ibetaPowerTerms( a, b, x, y, normalized ) {
	var result;
	var smallA;
	var ratio;
	var agh;
	var bgh;
	var cgh;
	var l1;
	var l2;
	var l3;
	var p1;
	var b1;
	var b2;
	var c;
	var l;

	if ( !normalized ) {
		// Can we do better here?
		return pow( x, a ) * pow( y, b );
	}
	c = a + b;

	// Combine power terms with Lanczos approximation:
	agh = a + G - 0.5;
	bgh = b + G - 0.5;
	cgh = c + G - 0.5;
	result = lanczosSumExpGScaled( c );
	result /= lanczosSumExpGScaled( a ) * lanczosSumExpGScaled( b );

	// Combine with the leftover terms from the Lanczos approximation:
	result *= sqrt( bgh / E );
	result *= sqrt( agh / cgh );

	// `l1` and `l2` are the base of the exponents minus one:
	l1 = ( ( x * b ) - ( y * agh ) ) / agh;
	l2 = ( ( y * a ) - ( x * bgh ) ) / bgh;
	if ( min( abs(l1), abs(l2) ) < 0.2 ) {
		// When the base of the exponent is very near 1 we get really gross errors unless extra care is taken:
		if ( l1 * l2 > 0 || min( a, b ) < 1 ) {
			if ( abs(l1) < 0.1 ) {
				result *= exp( a * log1p( l1 ) );
			} else {
				result *= pow( ( x*cgh ) / agh, a );
			}
			if ( abs(l2) < 0.1 ) {
				result *= exp( b * log1p( l2 ) );
			} else {
				result *= pow((y * cgh) / bgh, b);
			}
		}
		else if ( max( abs(l1), abs(l2) ) < 0.5 ) {
			smallA = a < b;
			ratio = b / a;
			if (
				(smallA && (ratio * l2 < 0.1)) ||
				(!smallA && (l1 / ratio > 0.1))
			) {
				l3 = expm1( ratio * log1p( l2 ) );
				l3 = l1 + l3 + ( l3 * l1 );
				l3 = a * log1p( l3 );
				result *= exp( l3 );
			}
			else {
				l3 = expm1( log1p( l1 ) / ratio );
				l3 = l2 + l3 + ( l3 * l2 );
				l3 = b * log1p( l3 );
				result *= exp( l3 );
			}
		}
		else if ( abs(l1) < abs(l2) ) {
			// First base near 1 only:
			l = ( a * log1p( l1 ) ) + ( b * ln( ( y*cgh ) / bgh ) );
			if ( l <= MIN_LN || l >= MAX_LN ) {
				l += ln(result);
				if ( l >= MAX_LN ) {
					return NaN;
				}
				result = exp( l );
			} else {
				result *= exp( l );
			}
		}
		else {
			// Second base near 1 only:
			l = ( b * log1p( l2 ) ) + ( a * ln( (x*cgh) / agh ) );
			if ( l <= MIN_LN || l >= MAX_LN ) {
				l += ln(result);
				if ( l >= MAX_LN ) {
					return NaN;
				}
				result = exp( l );
			} else {
				result *= exp( l );
			}
		}
	}
	else {
		// General case:
		b1 = (x * cgh) / agh;
		b2 = (y * cgh) / bgh;
		l1 = a * ln(b1);
		l2 = b * ln(b2);
		if (
			l1 >= MAX_LN ||
			l1 <= MIN_LN ||
			l2 >= MAX_LN ||
			l2 <= MIN_LN
		) {
			// Oops, under/overflow, sidestep if we can:
			if ( a < b ) {
				p1 = pow( b2, b / a );
				l3 = a * ( ln(b1) + ln(p1) );
				if ( l3 < MAX_LN && l3 > MIN_LN ) {
					result *= pow( p1 * b1, a );
				} else {
					l2 += l1 + ln(result);
					if ( l2 >= MAX_LN ) {
						return NaN;
					}
					result = exp( l2 );
				}
			}
			else {
				p1 = pow( b1, a / b );
				l3 = ( ln(p1) + ln(b2) ) * b;
				if ( l3 < MAX_LN && l3 > MIN_LN ) {
					result *= pow( p1 * b2, b );
				} else {
					l2 += l1 + ln( result );
					if (l2 >= MAX_LN) {
						return NaN;
					}
					result = exp( l2 );
				}
			}
		}
		else {
			// Finally the normal case:
			result *= pow( b1, a ) * pow( b2, b );
		}
	}
	return result;
} // end FUNCTION ibetaPowerTerms()

// EXPORTS //

module.exports = ibetaPowerTerms;
<commit_msg>Use minabs and maxabs functions<commit_after>'use strict';

/*
* The original C++ code and copyright notice is from the [Boost library]{@link http://www.boost.org/doc/libs/1_62_0/boost/math/special_functions/beta.hpp}.
*
* The implementation has been modified for JavaScript.
*/

/*
* (C) Copyright John Maddock 2006.
* Use, modification and distribution are subject to the
* Boost Software License, Version 1.0. (See accompanying file
* LICENSE or copy at http://www.boost.org/LICENSE_1_0.txt)
*/

// MODULES //

var lanczosSumExpGScaled = require( '@stdlib/math/base/special/gamma-lanczos-sum-expg-scaled' );
var maxabs = require( '@stdlib/math/base/special/maxabs' );
var minabs = require( '@stdlib/math/base/special/minabs' );
var expm1 = require( '@stdlib/math/base/special/expm1' );
var log1p = require( '@stdlib/math/base/special/log1p' );
var sqrt = require( '@stdlib/math/base/special/sqrt' );
var abs = require( '@stdlib/math/base/special/abs' );
var exp = require( '@stdlib/math/base/special/exp' );
var pow = require( '@stdlib/math/base/special/pow' );
var min = require( '@stdlib/math/base/special/min' );
var ln = require( '@stdlib/math/base/special/ln' );
var MAX_LN = require( '@stdlib/math/constants/float64-max-ln' );
var MIN_LN = require( '@stdlib/math/constants/float64-min-ln' );
var G = require( '@stdlib/math/constants/float64-gamma-lanczos-g' );
var E = require( '@stdlib/math/constants/float64-e' );

// MAIN //

/**
* Computes the leading power terms in the incomplete beta function. When normalized,
*
* ```tex
* \frac{ x^a y^b }{ \operatorname{Beta}(a,b) }
* ```
*
* and otherwise
*
* ```tex
* x^a y^b
* ```
*
* #### Notes
*
* - Almost all of the error in the incomplete beta comes from this function, particularly when \\( a \\) and \\( b \\) are large. Computing large powers are *hard* though, and using logarithms just leads to horrendous cancellation errors.
* - For \\( l1 * l2 > 0 \\) or \\( \operatorname{min}( a, b ) < 1 \\), the two power terms both go in the same direction (toward zero or toward infinity). In this case if either term overflows or underflows, then the product of the two must do so also. Alternatively, if one exponent is less than one, then we can't productively use it to eliminate overflow or underflow from the other term.  Problems with spurious overflow/underflow can't be ruled out. In this case, but it is *very* unlikely since one of the power terms will evaluate to a number close to 1.
* - If \\( \max( \abs(l1), \abs(l2) ) < 0.5 \\), both exponents are near one and both the exponents are greater than one, and, further, these two power terms tend in opposite directions (one toward zero, the other toward infinity), so we have to combine the terms to avoid any risk of overflow or underflow. We do this by moving one power term inside the other, we have:
*
*    ```tex
*    (1 + l_1)^a \cdot (1 + l_2)^b \\
*    = ((1 + l_1) \cdot (1 + l_2)^(b/a))^a \\
*    = (1 + l_1 + l_3 + l_1*l_3)^a
*    ```
*
*    and
*
*    ```tex
*    l_3 = (1 + l_2)^(b/a) - 1 \\
*    = \exp((b/a) * \ln(1 + l_2)) - 1
*    ```
*
*    The tricky bit is deciding which term to move inside. By preference, we move the larger term inside, so that the size of the largest exponent is reduced.  However, that can only be done as long as l3 (see above) is also small.
*
* @private
* @param {NonNegativeNumber} a - function parameter
* @param {NonNegativeNumber} b - function parameter
* @param {Probability} x - function parameter
* @param {Probability} y - probability equal to `1-x`
* @param {boolean} normalized - boolean indicating whether to evaluate the power terms of the regularized or non-regularized incomplete beta function
* @returns {number} power terms
*/
function ibetaPowerTerms( a, b, x, y, normalized ) {
	var result;
	var smallA;
	var ratio;
	var agh;
	var bgh;
	var cgh;
	var l1;
	var l2;
	var l3;
	var p1;
	var b1;
	var b2;
	var c;
	var l;

	if ( !normalized ) {
		// Can we do better here?
		return pow( x, a ) * pow( y, b );
	}
	c = a + b;

	// Combine power terms with Lanczos approximation:
	agh = a + G - 0.5;
	bgh = b + G - 0.5;
	cgh = c + G - 0.5;
	result = lanczosSumExpGScaled( c );
	result /= lanczosSumExpGScaled( a ) * lanczosSumExpGScaled( b );

	// Combine with the leftover terms from the Lanczos approximation:
	result *= sqrt( bgh / E );
	result *= sqrt( agh / cgh );

	// `l1` and `l2` are the base of the exponents minus one:
	l1 = ( ( x * b ) - ( y * agh ) ) / agh;
	l2 = ( ( y * a ) - ( x * bgh ) ) / bgh;
	if ( minabs( l1, l2 ) < 0.2 ) {
		// When the base of the exponent is very near 1 we get really gross errors unless extra care is taken:
		if ( l1 * l2 > 0 || min( a, b ) < 1 ) {
			if ( abs(l1) < 0.1 ) {
				result *= exp( a * log1p( l1 ) );
			} else {
				result *= pow( ( x*cgh ) / agh, a );
			}
			if ( abs(l2) < 0.1 ) {
				result *= exp( b * log1p( l2 ) );
			} else {
				result *= pow((y * cgh) / bgh, b);
			}
		}
		else if ( maxabs( l1, l2 ) < 0.5 ) {
			smallA = a < b;
			ratio = b / a;
			if (
				(smallA && (ratio * l2 < 0.1)) ||
				(!smallA && (l1 / ratio > 0.1))
			) {
				l3 = expm1( ratio * log1p( l2 ) );
				l3 = l1 + l3 + ( l3 * l1 );
				l3 = a * log1p( l3 );
				result *= exp( l3 );
			}
			else {
				l3 = expm1( log1p( l1 ) / ratio );
				l3 = l2 + l3 + ( l3 * l2 );
				l3 = b * log1p( l3 );
				result *= exp( l3 );
			}
		}
		else if ( abs(l1) < abs(l2) ) {
			// First base near 1 only:
			l = ( a * log1p( l1 ) ) + ( b * ln( ( y*cgh ) / bgh ) );
			if ( l <= MIN_LN || l >= MAX_LN ) {
				l += ln(result);
				if ( l >= MAX_LN ) {
					return NaN;
				}
				result = exp( l );
			} else {
				result *= exp( l );
			}
		}
		else {
			// Second base near 1 only:
			l = ( b * log1p( l2 ) ) + ( a * ln( (x*cgh) / agh ) );
			if ( l <= MIN_LN || l >= MAX_LN ) {
				l += ln(result);
				if ( l >= MAX_LN ) {
					return NaN;
				}
				result = exp( l );
			} else {
				result *= exp( l );
			}
		}
	}
	else {
		// General case:
		b1 = (x * cgh) / agh;
		b2 = (y * cgh) / bgh;
		l1 = a * ln(b1);
		l2 = b * ln(b2);
		if (
			l1 >= MAX_LN ||
			l1 <= MIN_LN ||
			l2 >= MAX_LN ||
			l2 <= MIN_LN
		) {
			// Oops, under/overflow, sidestep if we can:
			if ( a < b ) {
				p1 = pow( b2, b / a );
				l3 = a * ( ln(b1) + ln(p1) );
				if ( l3 < MAX_LN && l3 > MIN_LN ) {
					result *= pow( p1 * b1, a );
				} else {
					l2 += l1 + ln(result);
					if ( l2 >= MAX_LN ) {
						return NaN;
					}
					result = exp( l2 );
				}
			}
			else {
				p1 = pow( b1, a / b );
				l3 = ( ln(p1) + ln(b2) ) * b;
				if ( l3 < MAX_LN && l3 > MIN_LN ) {
					result *= pow( p1 * b2, b );
				} else {
					l2 += l1 + ln( result );
					if (l2 >= MAX_LN) {
						return NaN;
					}
					result = exp( l2 );
				}
			}
		}
		else {
			// Finally the normal case:
			result *= pow( b1, a ) * pow( b2, b );
		}
	}
	return result;
} // end FUNCTION ibetaPowerTerms()

// EXPORTS //

module.exports = ibetaPowerTerms;
<|endoftext|>


<commit_before>import uniq from 'lodash/array/uniq';

import Polymer from '../polymer';

export default new Polymer({
  is: 'state-history-chart-line',

  properties: {
    data: {
      type: Object,
      observer: 'dataChanged',
    },

    unit: {
      type: String,
    },

    isSingleDevice: {
      type: Boolean,
      value: false,
    },

    isAttached: {
      type: Boolean,
      value: false,
      observer: 'dataChanged',
    },

    chartEngine: {
      type: Object,
    },
  },

  created() {
    this.style.display = 'block';
  },

  attached() {
    this.isAttached = true;
  },

  dataChanged() {
    this.drawChart();
  },

  drawChart() {
    if (!this.isAttached) {
      return;
    }

    if (!this.chartEngine) {
      this.chartEngine = new window.google.visualization.LineChart(this);
    }

    const unit = this.unit;
    const deviceStates = this.data;

    if (deviceStates.length === 0) {
      return;
    }

    const dataTable = new window.google.visualization.DataTable();

    dataTable.addColumn({ type: 'datetime', id: 'Time' });

    const options = {
      legend: { position: 'top' },
      titlePosition: 'none',
      vAxes: {
        // Adds units to the left hand side of the graph
        0: {title: unit},
      },
      hAxis: {
        format: 'H:mm',
      },
      lineWidth: 1,
      chartArea: { left: '60', width: '95%'},
      explorer: {
        actions: ['dragToZoom', 'rightClickToReset', 'dragToPan'],
        keepInBounds: true,
        axis: 'horizontal',
        maxZoomIn: 0.1,
      },
    };

    if (this.isSingleDevice) {
      options.legend.position = 'none';
      options.vAxes[0].title = null;
      options.chartArea.left = 40;
      options.chartArea.height = '80%';
      options.chartArea.top = 5;
      options.enableInteractivity = false;
    }

    // Get a unique list of times of state changes for all the devices
    let times = uniq(deviceStates.map(
                  states => states.map(
                    state => state.lastChangedAsDate)).reduce(
                      (tot, cur) => tot.concat(cur), [])).sort();

    // end time is Math.min(curTime, start time + 1 day)
    let endTime = new Date(times[0]);
    endTime.setDate(endTime.getDate() + 1);
    if (endTime > new Date()) {
      endTime = new Date();
    }

    times = times.concat(endTime);

    // This is going to be an array of arrays. Each array contains:
    // [Time, valueSensor1, valueSensor2, etc]

    // Google Graph requires each data series to have an entry for each point.
    // Since not all sensors have a value for each time, we'll put in the last
    // known value at that point in time.

    // Because we put in last known value, the 'average' line shown between
    // times is incorrect. To fix this, we add each time twice and have
    // transitions shown as a vertical line :-(

    const data = [];
    times.forEach(time => {
      data.push([time]);
      data.push([time]);
    });

    deviceStates.forEach(states => {
      let startIndex = 0;
      let curTime;
      let curValue;

      const nextState = function nextState() {
        if (startIndex === null) {
          return;
        }
        let value;
        for (let ind = startIndex; ind < states.length; ind++) {
          value = parseFloat(states[ind].state);
          if (!isNaN(value) && isFinite(value)) {
            startIndex = ind + 1;
            curValue = value;
            curTime = states[ind].lastChangedAsDate;
            return;
          }
        }
        startIndex = null;
      };

      nextState();

      // no usable states found.
      if (startIndex === null) {
        return;
      }

      dataTable.addColumn('number', states[states.length - 1].entityDisplay);

      times.forEach((time, index) => {
        data[index * 2].push(curValue);
        if (curTime === time) {
          nextState();
        }
        data[index * 2 + 1].push(curValue);
      });
    });

    dataTable.addRows(data);
    this.chartEngine.draw(dataTable, options);
  },
});
<commit_msg>Improve chart rendering<commit_after>import range from 'lodash/utility/range';

import Polymer from '../polymer';

export default new Polymer({
  is: 'state-history-chart-line',

  properties: {
    data: {
      type: Object,
      observer: 'dataChanged',
    },

    unit: {
      type: String,
    },

    isSingleDevice: {
      type: Boolean,
      value: false,
    },

    isAttached: {
      type: Boolean,
      value: false,
      observer: 'dataChanged',
    },

    chartEngine: {
      type: Object,
    },
  },

  created() {
    this.style.display = 'block';
  },

  attached() {
    this.isAttached = true;
  },

  dataChanged() {
    this.drawChart();
  },

  drawChart() {
    if (!this.isAttached) {
      return;
    }

    if (!this.chartEngine) {
      this.chartEngine = new window.google.visualization.LineChart(this);
    }

    const unit = this.unit;
    const deviceStates = this.data;

    if (deviceStates.length === 0) {
      return;
    }

    const options = {
      legend: { position: 'top' },
      interpolateNulls: true,
      titlePosition: 'none',
      vAxes: {
        // Adds units to the left hand side of the graph
        0: {title: unit},
      },
      hAxis: {
        format: 'H:mm',
      },
      lineWidth: 1,
      chartArea: { left: '60', width: '95%'},
      explorer: {
        actions: ['dragToZoom', 'rightClickToReset', 'dragToPan'],
        keepInBounds: true,
        axis: 'horizontal',
        maxZoomIn: 0.1,
      },
    };

    if (this.isSingleDevice) {
      options.legend.position = 'none';
      options.vAxes[0].title = null;
      options.chartArea.left = 40;
      options.chartArea.height = '80%';
      options.chartArea.top = 5;
      options.enableInteractivity = false;
    }

    const startTime = new Date(Math.min.apply(
      null, deviceStates.map(states => states[0].lastChangedAsDate)));

    let endTime = new Date(startTime);
    endTime.setDate(endTime.getDate() + 1);
    if (endTime > new Date()) {
      endTime = new Date();
    }

    const dataTables = deviceStates.map(states => {
      // Only do interpolation for sensors, makes no sense for ie. thermostat
      const noInterpolation = states[0].domain !== 'sensor';

      const dataTable = new window.google.visualization.DataTable();
      dataTable.addColumn({ type: 'datetime', id: 'Time' });
      dataTable.addColumn('number', states[states.length - 1].entityDisplay);
      const data = [];

      let prevValue;

      states.forEach(state => {
        const value = parseFloat(state.state);
        if (!isNaN(value) && isFinite(value)) {
          if (noInterpolation) {
            data.push([state.lastChangedAsDate, prevValue]);
          }
          data.push([state.lastChangedAsDate, value]);
          prevValue = value;
        }
      });

      data.push([endTime, prevValue]);

      dataTable.addRows(data);
      return dataTable;
    });

    let finalDataTable;

    if (dataTables.length === 1) {
      finalDataTable = dataTables[0];
    } else {
      finalDataTable = dataTables.slice(1).reduce(
        (tot, cur) => window.google.visualization.data.join(
          tot, cur, 'full', [[0, 0]], range(1, tot.getNumberOfColumns()), [1]),
        dataTables[0]);
    }

    this.chartEngine.draw(finalDataTable, options);
  },
});
<|endoftext|>


<commit_before>/**
 * # StorageDriver
 *
 * @param {String} hash_code
 * @param {Redis client} client
 */

/*! */

/* global -Promise */
let Promise = require('promise');
let redis = require('redis');

module.exports = function storageDriver(hash_code, client = redis.createClient()) {
  let create_promise = (callback, key = '') => {
    return new Promise((resolve, reject) => {
      let redisCallback = (err, data) => {
        if (err !== null) { reject(err); }
        else { resolve(callback(data)); }
      };
      if (key === '') { client.hgetall(hash_code, redisCallback); }
      else { client.hget(hash_code, key, redisCallback); }
    });
  };

  return {

    /**
     * Get name
     *
     * @method getName
     * @returns the name
     */

    getName() {
      return create_promise(data => data, 'name');
    },

      /**
       * Change name
       *
       * @method setName
       * @param {String} name
       */

      setName(name) {
        client.hset(hash_code, 'name', name);
      },

      /**
       * Get data
       *
       * @method getData
       * @returns the JSON
       */

      getData() {
        return create_promise(data => JSON.parse(data), 'data');
      },

        /**
         * Change data
         *
         * @method setData
         * @param {JSON} json
         */

        setData(json) {
          client.hset(hash_code, 'data', JSON.stringify(json));
        },

        /**
         * Get JSON
         *
         * @method getJSON
         * @returns all data as JSON
         */

        getJSON() {
          return create_promise(data => {
            // Return empty document if nothing in db
            if (typeof data === 'undefined' || data === null) {
              return { name: '', data: {} };
            }

            // Else return the document
            data.data = JSON.parse(data.data);
            return data;
          });
        },

          /**
           * Disconnects from redis
           *
           * @method disconnect
           */

          disconnect() {
            client.quit();
          }
  };
};
<commit_msg>Fix weird indentention<commit_after>/**
 * # StorageDriver
 *
 * @param {String} hash_code
 * @param {Redis client} client
 */

/*! */

/* global -Promise */
let Promise = require('promise');
let redis = require('redis');

module.exports = function storageDriver(hash_code, client = redis.createClient()) {
  let create_promise = (callback, key = '') => {
    return new Promise((resolve, reject) => {
      let redisCallback = (err, data) => {
        if (err !== null) { reject(err); }
        else { resolve(callback(data)); }
      };
      if (key === '') { client.hgetall(hash_code, redisCallback); }
      else { client.hget(hash_code, key, redisCallback); }
    });
  };

  return {

    /**
     * Get name
     *
     * @method getName
     * @returns the name
     */

    getName() {
      return create_promise(data => data, 'name');
    },

      /**
       * Change name
       *
       * @method setName
       * @param {String} name
       */

      setName(name) {
        client.hset(hash_code, 'name', name);
      },

      /**
       * Get data
       *
       * @method getData
       * @returns the JSON
       */

      getData() {
        return create_promise(data => JSON.parse(data), 'data');
      },

      /**
       * Change data
       *
       * @method setData
       * @param {JSON} json
       */

      setData(json) {
        client.hset(hash_code, 'data', JSON.stringify(json));
      },

      /**
       * Get JSON
       *
       * @method getJSON
       * @returns all data as JSON
       */

      getJSON() {
        return create_promise(data => {
          // Return empty document if nothing in db
          if (typeof data === 'undefined' || data === null) {
            return { name: '', data: {} };
          }

          // Else return the document
          data.data = JSON.parse(data.data);
          return data;
        });
      },

      /**
       * Disconnects from redis
       *
       * @method disconnect
       */

      disconnect() {
        client.quit();
      }
  };
};
<|endoftext|>


<commit_before>// Copyright 2010-2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
// Licensed under the Apache-2.0 License on an "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND.

// ABOUT THIS NODE.JS SAMPLE: This sample is part of the SDK for JavaScript Developer Guide topic at
// https://docs.aws.amazon.com/sdk-for-javascript/v2/developer-guide/sns-examples-managing-topics.html
// Load the AWS SDK for Node.js
var AWS = require('aws-sdk');
// Set region
AWS.config.update({region: 'us-west-2'});

// Create promise and SNS service object
var deleteTopicPromise = new AWS.SNS({apiVersion: '2010-03-31'}).deleteTopic({TopicArn: 'arn:aws:sns:us-west-2:617985816162:FirstTopic'}).promise();

// handle promise's fulfilled/rejected states
deleteTopicPromise.then(
  function(data) {
    console.log("Topic Deleted");
  }).catch(
    function(err) {
    console.error(err, err.stack);
  });
<commit_msg>Update sns_deletetopic.js<commit_after>// Copyright 2010-2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
// Licensed under the Apache-2.0 License on an "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND.

// ABOUT THIS NODE.JS SAMPLE: This sample is part of the SDK for JavaScript Developer Guide topic at
// https://docs.aws.amazon.com/sdk-for-javascript/v2/developer-guide/sns-examples-managing-topics.html
// Load the AWS SDK for Node.js
var AWS = require('aws-sdk');
// Set region
AWS.config.update({region: 'us-west-2'});

// Create promise and SNS service object
var deleteTopicPromise = new AWS.SNS({apiVersion: '2010-03-31'}).deleteTopic({TopicArn: 'TOPIC_ARN'}).promise();

// handle promise's fulfilled/rejected states
deleteTopicPromise.then(
  function(data) {
    console.log("Topic Deleted");
  }).catch(
    function(err) {
    console.error(err, err.stack);
  });
<|endoftext|>


<commit_before>/* eslint-disable no-param-reassign */

import Vue from 'vue';

import search from './packages/search';
import uploads from './packages/uploads';

const filterInvisiblePackages = (pkg) => {
    return pkg.name !== 'contao/manager-bundle' && pkg.name !== 'contao/conflicts';
};

export default {
    namespaced: true,

    modules: {
        search,
        uploads,
    },

    state: {
        installed: null,
        required: {},
        add: {},
        change: {},
        update: [],
        remove: [],
    },

    getters: {
        hasAdded: state => Object.keys(state.add).length > 0 || Object.keys(state.required).length > 0,

        packageInstalled: state => name => Object.keys(state.installed).includes(name),
        packageRequired: state => name => Object.keys(state.required).includes(name),
        packageAdded: state => name => Object.keys(state.add).includes(name),
        packageChanged: state => name => Object.keys(state.change).includes(name),
        packageUpdated: state => name => state.update.includes(name),
        packageRemoved: state => name => state.remove.includes(name),

        totalChanges: state => Object.keys(state.add).length
            + Object.keys(state.required).length
            + Object.keys(state.change).length
            + state.update.length
            + state.remove.length
            - Object.values(state.change).filter(p => Object.keys(state.required).includes(p.name)).length
            - state.remove.filter(p => Object.keys(state.required).includes(p)).length,

        totalRequired: state => Object.keys(state.required).length
            - Object.values(state.change).filter(pkg => Object.keys(state.required).includes(pkg.name)).length
            - state.remove.filter(pkg => Object.keys(state.required).includes(pkg)).length,

        canResetChanges: (s, get) => get.totalChanges > get.totalRequired,

        visibleInstalled: s => Object.values(s.installed).filter(filterInvisiblePackages),
        visibleRequired: s => Object.values(s.required).filter(filterInvisiblePackages),
    },

    mutations: {
        setInstalled(state, packages) {
            if (packages === null) {
                state.installed = null;
                state.required = {};
                return;
            }

            const installed = {};
            const required = {};

            Object.keys(packages).forEach((name) => {
                if (packages[name].version === false) {
                    required[name] = packages[name];
                } else {
                    installed[name] = packages[name];
                }
            });

            state.installed = installed;
            state.required = required;
        },

        add(state, pkg) {
            if (!state.add[pkg.name] && !state.required[pkg.name]) {
                Vue.set(state.add, pkg.name, pkg);
            }
        },

        change(state, { name, version }) {
            this.commit('packages/restore', name);
            Vue.set(state.change, name, version);
        },

        update(state, name) {
            this.commit('packages/restore', name);
            state.update.push(name);
        },

        updateAll(state) {
            Object.keys(state.installed).forEach((name) => {
                state.update.push(name);
            });
        },

        remove(state, name) {
            this.commit('packages/restore', name);
            state.remove.push(name);
        },

        restore(state, name) {
            Vue.delete(state.add, name);
            Vue.delete(state.change, name);

            if (state.remove.includes(name)) {
                state.remove.splice(state.remove.indexOf(name), 1);
            }

            if (state.update.includes(name)) {
                state.update.splice(state.update.indexOf(name), 1);
            }
        },

        reset(state) {
            state.add = {};
            state.change = {};
            state.update = [];
            state.remove = [];
        },
    },

    actions: {
        async load({ commit }) {
            commit('setInstalled', null);
            commit('reset');

            const packages = {};
            const load = [
                Vue.http.get('api/packages/root'),
                Vue.http.get('api/packages/local'),
            ];
            const root = (await load[0]).body;
            const local = (await load[1]).body;

            Object.keys(root.require).forEach((require) => {
                if (!require.includes('/')) {
                    return;
                }

                packages[require] = {
                    name: require,
                    version: false,
                    constraint: root.require[require],
                };

                if (local[require]) {
                    packages[require] = Object.assign(packages[require], local[require]);
                }
            });

            commit('setInstalled', packages);

            return packages;
        },

        apply({ state, dispatch }, dryRun = false) {
            const require = state.change;
            const remove = state.remove;
            const update = state.update.concat(
                Object.keys(state.required),
                Object.keys(state.change).filter(pkg => !Object.keys(state.required).includes(pkg)),
                state.remove.filter(pkg => !Object.keys(state.required).includes(pkg)),
            );

            Object.keys(state.add).forEach((pkg) => {
                require[state.add[pkg].name] = state.add[pkg].constraint || null;
                update.push(state.add[pkg].name);
            });

            const task = {
                name: 'composer/update',
                config: {
                    require,
                    remove,
                    update,
                    uploads: true,
                    dry_run: dryRun === true,
                },
            };

            return dispatch('tasks/execute', task, { root: true });
        },
    },
};
<commit_msg>Fixed version constraint not being updated<commit_after>/* eslint-disable no-param-reassign */

import Vue from 'vue';

import search from './packages/search';
import uploads from './packages/uploads';

const filterInvisiblePackages = (pkg) => {
    return pkg.name !== 'contao/manager-bundle' && pkg.name !== 'contao/conflicts';
};

export default {
    namespaced: true,

    modules: {
        search,
        uploads,
    },

    state: {
        installed: null,
        required: {},
        add: {},
        change: {},
        update: [],
        remove: [],
    },

    getters: {
        hasAdded: state => Object.keys(state.add).length > 0 || Object.keys(state.required).length > 0,

        packageInstalled: state => name => Object.keys(state.installed).includes(name),
        packageRequired: state => name => Object.keys(state.required).includes(name),
        packageAdded: state => name => Object.keys(state.add).includes(name),
        packageChanged: state => name => Object.keys(state.change).includes(name),
        packageUpdated: state => name => state.update.includes(name),
        packageRemoved: state => name => state.remove.includes(name),

        totalChanges: state => Object.keys(state.add).length
            + Object.keys(state.required).length
            + Object.keys(state.change).length
            + state.update.length
            + state.remove.length
            - Object.values(state.change).filter(p => Object.keys(state.required).includes(p.name)).length
            - state.remove.filter(p => Object.keys(state.required).includes(p)).length,

        totalRequired: state => Object.keys(state.required).length
            - Object.values(state.change).filter(pkg => Object.keys(state.required).includes(pkg.name)).length
            - state.remove.filter(pkg => Object.keys(state.required).includes(pkg)).length,

        canResetChanges: (s, get) => get.totalChanges > get.totalRequired,

        visibleInstalled: s => Object.values(s.installed).filter(filterInvisiblePackages),
        visibleRequired: s => Object.values(s.required).filter(filterInvisiblePackages),
    },

    mutations: {
        setInstalled(state, packages) {
            if (packages === null) {
                state.installed = null;
                state.required = {};
                return;
            }

            const installed = {};
            const required = {};

            Object.keys(packages).forEach((name) => {
                if (packages[name].version === false) {
                    required[name] = packages[name];
                } else {
                    installed[name] = packages[name];
                }
            });

            state.installed = installed;
            state.required = required;
        },

        add(state, pkg) {
            Vue.set(state.add, pkg.name, pkg);
        },

        change(state, { name, version }) {
            this.commit('packages/restore', name);
            Vue.set(state.change, name, version);
        },

        update(state, name) {
            this.commit('packages/restore', name);
            state.update.push(name);
        },

        updateAll(state) {
            Object.keys(state.installed).forEach((name) => {
                state.update.push(name);
            });
        },

        remove(state, name) {
            this.commit('packages/restore', name);
            state.remove.push(name);
        },

        restore(state, name) {
            Vue.delete(state.add, name);
            Vue.delete(state.change, name);

            if (state.remove.includes(name)) {
                state.remove.splice(state.remove.indexOf(name), 1);
            }

            if (state.update.includes(name)) {
                state.update.splice(state.update.indexOf(name), 1);
            }
        },

        reset(state) {
            state.add = {};
            state.change = {};
            state.update = [];
            state.remove = [];
        },
    },

    actions: {
        async load({ commit }) {
            commit('setInstalled', null);
            commit('reset');

            const packages = {};
            const load = [
                Vue.http.get('api/packages/root'),
                Vue.http.get('api/packages/local'),
            ];
            const root = (await load[0]).body;
            const local = (await load[1]).body;

            Object.keys(root.require).forEach((require) => {
                if (!require.includes('/')) {
                    return;
                }

                packages[require] = {
                    name: require,
                    version: false,
                    constraint: root.require[require],
                };

                if (local[require]) {
                    packages[require] = Object.assign(packages[require], local[require]);
                }
            });

            commit('setInstalled', packages);

            return packages;
        },

        apply({ state, dispatch }, dryRun = false) {
            const require = state.change;
            const remove = state.remove;
            const update = state.update.concat(
                Object.keys(state.required),
                Object.keys(state.change).filter(pkg => !Object.keys(state.required).includes(pkg)),
                state.remove.filter(pkg => !Object.keys(state.required).includes(pkg)),
            );

            Object.keys(state.add).forEach((pkg) => {
                require[state.add[pkg].name] = state.add[pkg].constraint || null;
                update.push(state.add[pkg].name);
            });

            const task = {
                name: 'composer/update',
                config: {
                    require,
                    remove,
                    update,
                    uploads: true,
                    dry_run: dryRun === true,
                },
            };

            return dispatch('tasks/execute', task, { root: true });
        },
    },
};
<|endoftext|>