<commit_before>import React, { Component } from 'react';
import {
  StyleSheet,
  Dimensions,
  Platform,
  View,
  TextInput,
  TouchableOpacity,
  Animated
} from 'react-native';
import PropTypes from 'prop-types';
import Icon from 'react-native-vector-icons/MaterialIcons';
import { filter, some, includes } from 'lodash/collection';
import { debounce } from 'lodash/function';

const INITIAL_TOP = Platform.OS === 'ios' ? -80 : -60;

export default class Search extends Component {
  static propTypes = {
    data: PropTypes.array,
    placeholder: PropTypes.string,
    handleChangeText: PropTypes.func,
    handleSearch: PropTypes.func,
    handleResults: PropTypes.func,
    onSubmitEditing: PropTypes.func,
    onFocus: PropTypes.func,
    onBlur: PropTypes.func,
    onHide: PropTypes.func,
    onBack: PropTypes.func,
    onX: PropTypes.func,
    backButton: PropTypes.object,
    backButtonAccessibilityLabel: PropTypes.string,
    closeButton: PropTypes.object,
    closeButtonAccessibilityLabel: PropTypes.string,
    backCloseSize: PropTypes.number,
    fontSize: PropTypes.number,
    heightAdjust: PropTypes.number,
    backgroundColor: PropTypes.string,
    iconColor: PropTypes.string,
    textColor: PropTypes.string,
    selectionColor: PropTypes.string,
    placeholderTextColor: PropTypes.string,
    animate: PropTypes.bool,
    animationDuration: PropTypes.number,
    showOnLoad: PropTypes.bool,
    hideBack: PropTypes.bool,
    hideX: PropTypes.bool,
    iOSPadding: PropTypes.bool,
    iOSHideShadow: PropTypes.bool,
    clearOnShow: PropTypes.bool,
    clearOnHide: PropTypes.bool,
    clearOnBlur: PropTypes.bool,
    focusOnLayout: PropTypes.bool,
    autoCorrect: PropTypes.bool,
    autoCapitalize: PropTypes.string,
    keyboardAppearance: PropTypes.string,
    keyboardType: PropTypes.string,
    fontFamily: PropTypes.string,
    allDataOnEmptySearch: PropTypes.bool,
    editable: PropTypes.bool
  };

  static defaultProps = {
    data: [],
    placeholder: 'Search',
    backButtonAccessibilityLabel: 'Navigate up',
    closeButtonAccessibilityLabel: 'Clear search text',
    heightAdjust: 0,
    backgroundColor: 'white',
    iconColor: 'gray',
    textColor: 'gray',
    selectionColor: 'lightskyblue',
    placeholderTextColor: 'lightgray',
    animate: true,
    animationDuration: 200,
    showOnLoad: false,
    hideBack: false,
    hideX: false,
    iOSPadding: true,
    iOSHideShadow: false,
    clearOnShow: false,
    clearOnHide: true,
    clearOnBlur: false,
    focusOnLayout: true,
    autoCorrect: true,
    autoCapitalize: 'sentences',
    keyboardAppearance: 'default',
    fontFamily: 'System',
    allDataOnEmptySearch: false,
    backCloseSize: 28,
    fontSize: 20,
    editable: true
  };

  constructor(props) {
    super(props);
    this.state = {
      input: '',
      show: props.showOnLoad,
      top: new Animated.Value(
        props.showOnLoad ? 0 : INITIAL_TOP + props.heightAdjust
      )
    };
  }

  getValue = () => {
    return this.state.input;
  };

  show = () => {
    const { animate, animationDuration, clearOnShow } = this.props;
    if (clearOnShow) {
      this.setState({ input: '' });
    }
    this.setState({ show: true });
    if (animate) {
      Animated.timing(this.state.top, {
        toValue: 0,
        duration: animationDuration
      }).start();
    } else {
      this.setState({ top: new Animated.Value(0) });
    }
  };

  hide = () => {
    const { onHide, animate, animationDuration } = this.props;
    if (onHide) {
      onHide(this.state.input);
    }
    if (animate) {
      Animated.timing(this.state.top, {
        toValue: INITIAL_TOP,
        duration: animationDuration
      }).start();
      const timerId = setTimeout(() => {
        this._doHide();
        clearTimeout(timerId);
      }, animationDuration);
    } else {
      this.setState({ top: new Animated.Value(INITIAL_TOP) });
      this._doHide();
    }
  };

  _doHide = () => {
    const { clearOnHide } = this.props;
    this.setState({ show: false });
    if (clearOnHide) {
      this.setState({ input: '' });
    }
  };

  _handleX = () => {
    const { onX } = this.props;
    this._clearInput();
    if (onX) onX();
  };

  _handleBlur = () => {
    const { onBlur, clearOnBlur } = this.props;
    if (onBlur) {
      onBlur();
    }
    if (clearOnBlur) {
      this._clearInput();
    }
  };

  _clearInput = () => {
    this.setState({ input: '' });
    this._onChangeText('');
  };

  _onChangeText = input => {
    const { handleChangeText, handleSearch, handleResults } = this.props;
    this.setState({ input });
    if (handleChangeText) {
      handleChangeText(input);
    }
    if (handleSearch) {
      handleSearch(input);
    } else {
      debounce(() => {
        // use internal search logic (depth first)!
        if (handleResults) {
          const results = this._internalSearch(input);
          handleResults(results);
        }
      }, 500)();
    }
  };

  _internalSearch = input => {
    const { data, allDataOnEmptySearch } = this.props;
    if (input === '') {
      return allDataOnEmptySearch ? data : [];
    }
    return filter(data, item => {
      return this._depthFirstSearch(item, input);
    });
  };

  _depthFirstSearch = (collection, input) => {
    // let's get recursive boi
    let type = typeof collection;
    // base case(s)
    if (type === 'string' || type === 'number' || type === 'boolean') {
      return includes(
        collection.toString().toLowerCase(),
        input.toString().toLowerCase()
      );
    }
    return some(collection, item => this._depthFirstSearch(item, input));
  };

  render = () => {
    const {
      placeholder,
      heightAdjust,
      backgroundColor,
      iconColor,
      textColor,
      selectionColor,
      placeholderTextColor,
      onBack,
      hideBack,
      hideX,
      iOSPadding,
      iOSHideShadow,
      onSubmitEditing,
      onFocus,
      focusOnLayout,
      autoCorrect,
      autoCapitalize,
      keyboardAppearance,
      fontFamily,
      backButton,
      backButtonAccessibilityLabel,
      closeButton,
      closeButtonAccessibilityLabel,
      backCloseSize,
      fontSize,
      editable,
      keyboardType
    } = this.props;
    return (
      <Animated.View
        style={[
          styles.container,
          {
            top: this.state.top,
            shadowOpacity: iOSHideShadow ? 0 : 0.7
          }
        ]}>
        {this.state.show && (
          <View style={[styles.navWrapper, { backgroundColor }]}>
            {Platform.OS === 'ios' &&
              iOSPadding && <View style={{ height: 20 }} />}
            <View
              style={[
                styles.nav,
                { height: (Platform.OS === 'ios' ? 52 : 62) + heightAdjust }
              ]}>
              {!hideBack && (
                <TouchableOpacity
                  accessible={true}
                  accessibilityComponentType="button"
                  accessibilityLabel={backButtonAccessibilityLabel}
                  onPress={onBack || this.hide}>
                  {backButton ? (
                    <View
                      style={{ width: backCloseSize, height: backCloseSize }}>
                      {backButton}
                    </View>
                  ) : (
                    <Icon
                      name="arrow-back"
                      size={backCloseSize}
                      style={{
                        color: iconColor,
                        padding: heightAdjust / 2 + 10
                      }}
                    />
                  )}
                </TouchableOpacity>
              )}
              <TextInput
                ref={ref => (this.textInput = ref)}
                onLayout={() => focusOnLayout && this.textInput.focus()}
                style={[
                  styles.input,
                  {
                    fontSize: fontSize,
                    color: textColor,
                    fontFamily: fontFamily,
                    marginLeft: hideBack ? 30 : 0,
                    marginTop: Platform.OS === 'ios' ? heightAdjust / 2 + 10 : 0
                  }
                ]}
                selectionColor={selectionColor}
                onChangeText={input => this._onChangeText(input)}
                onSubmitEditing={() =>
                  onSubmitEditing ? onSubmitEditing() : null}
                onFocus={() => (onFocus ? onFocus() : null)}
                onBlur={this._handleBlur}
                placeholder={placeholder}
                placeholderTextColor={placeholderTextColor}
                value={this.state.input}
                underlineColorAndroid="transparent"
                returnKeyType="search"
                autoCorrect={autoCorrect}
                autoCapitalize={autoCapitalize}
                keyboardType={keyboardType || "default"}
                keyboardAppearance={keyboardAppearance}
                editable={editable}
              />
              <TouchableOpacity
                accessible={true}
                accessibilityComponentType="button"
                accessibilityLabel={closeButtonAccessibilityLabel}
                onPress={
                  hideX || this.state.input === '' ? null : this._handleX
                }>
                {closeButton ? (
                  <View style={{ width: backCloseSize, height: backCloseSize }}>
                    {closeButton}
                  </View>
                ) : (
                  <Icon
                    name={'close'}
                    size={backCloseSize}
                    style={{
                      color:
                        hideX || this.state.input == ''
                          ? backgroundColor
                          : iconColor,
                      padding: heightAdjust / 2 + 10
                    }}
                  />
                )}
              </TouchableOpacity>
            </View>
          </View>
        )}
      </Animated.View>
    );
  };
}

const styles = StyleSheet.create({
  container: {
    flex: 1,
    zIndex: 10,
    position: 'absolute',
    elevation: 2,
    shadowRadius: 5
  },
  navWrapper: {
    width: Dimensions.get('window').width
  },
  nav: {
    ...Platform.select({
      android: {
        borderBottomColor: 'lightgray',
        borderBottomWidth: StyleSheet.hairlineWidth
      }
    }),
    flex: 1,
    flexBasis: 1,
    flexDirection: 'row',
    justifyContent: 'space-around',
    alignItems: 'center'
  },
  input: {
    ...Platform.select({
      ios: { height: 30 },
      android: { height: 50 }
    }),
    width: Dimensions.get('window').width - 120
  }
});
<commit_msg>performance: useNativeDriver for animations<commit_after>import React, { Component } from 'react';
import {
  StyleSheet,
  Dimensions,
  Platform,
  View,
  TextInput,
  TouchableOpacity,
  Animated
} from 'react-native';
import PropTypes from 'prop-types';
import Icon from 'react-native-vector-icons/MaterialIcons';
import { filter, some, includes } from 'lodash/collection';
import { debounce } from 'lodash/function';

const INITIAL_TOP = Platform.OS === 'ios' ? -80 : -60;

export default class Search extends Component {
  static propTypes = {
    data: PropTypes.array,
    placeholder: PropTypes.string,
    handleChangeText: PropTypes.func,
    handleSearch: PropTypes.func,
    handleResults: PropTypes.func,
    onSubmitEditing: PropTypes.func,
    onFocus: PropTypes.func,
    onBlur: PropTypes.func,
    onHide: PropTypes.func,
    onBack: PropTypes.func,
    onX: PropTypes.func,
    backButton: PropTypes.object,
    backButtonAccessibilityLabel: PropTypes.string,
    closeButton: PropTypes.object,
    closeButtonAccessibilityLabel: PropTypes.string,
    backCloseSize: PropTypes.number,
    fontSize: PropTypes.number,
    heightAdjust: PropTypes.number,
    backgroundColor: PropTypes.string,
    iconColor: PropTypes.string,
    textColor: PropTypes.string,
    selectionColor: PropTypes.string,
    placeholderTextColor: PropTypes.string,
    animate: PropTypes.bool,
    animationDuration: PropTypes.number,
    showOnLoad: PropTypes.bool,
    hideBack: PropTypes.bool,
    hideX: PropTypes.bool,
    iOSPadding: PropTypes.bool,
    iOSHideShadow: PropTypes.bool,
    clearOnShow: PropTypes.bool,
    clearOnHide: PropTypes.bool,
    clearOnBlur: PropTypes.bool,
    focusOnLayout: PropTypes.bool,
    autoCorrect: PropTypes.bool,
    autoCapitalize: PropTypes.string,
    keyboardAppearance: PropTypes.string,
    keyboardType: PropTypes.string,
    fontFamily: PropTypes.string,
    allDataOnEmptySearch: PropTypes.bool,
    editable: PropTypes.bool
  };

  static defaultProps = {
    data: [],
    placeholder: 'Search',
    backButtonAccessibilityLabel: 'Navigate up',
    closeButtonAccessibilityLabel: 'Clear search text',
    heightAdjust: 0,
    backgroundColor: 'white',
    iconColor: 'gray',
    textColor: 'gray',
    selectionColor: 'lightskyblue',
    placeholderTextColor: 'lightgray',
    animate: true,
    animationDuration: 200,
    showOnLoad: false,
    hideBack: false,
    hideX: false,
    iOSPadding: true,
    iOSHideShadow: false,
    clearOnShow: false,
    clearOnHide: true,
    clearOnBlur: false,
    focusOnLayout: true,
    autoCorrect: true,
    autoCapitalize: 'sentences',
    keyboardAppearance: 'default',
    fontFamily: 'System',
    allDataOnEmptySearch: false,
    backCloseSize: 28,
    fontSize: 20,
    editable: true
  };

  constructor(props) {
    super(props);
    this.state = {
      input: '',
      show: props.showOnLoad,
      top: new Animated.Value(
        props.showOnLoad ? 0 : INITIAL_TOP + props.heightAdjust
      )
    };
  }

  getValue = () => {
    return this.state.input;
  };

  show = () => {
    const { animate, animationDuration, clearOnShow } = this.props;
    if (clearOnShow) {
      this.setState({ input: '' });
    }
    this.setState({ show: true });
    if (animate) {
      Animated.timing(this.state.top, {
        toValue: 0,
        duration: animationDuration,
        useNativeDriver: true,
      }).start();
    } else {
      this.setState({ top: new Animated.Value(0) });
    }
  };

  hide = () => {
    const { onHide, animate, animationDuration } = this.props;
    if (onHide) {
      onHide(this.state.input);
    }
    if (animate) {
      Animated.timing(this.state.top, {
        toValue: INITIAL_TOP,
        duration: animationDuration,
        useNativeDriver: true,
      }).start();
      const timerId = setTimeout(() => {
        this._doHide();
        clearTimeout(timerId);
      }, animationDuration);
    } else {
      this.setState({ top: new Animated.Value(INITIAL_TOP) });
      this._doHide();
    }
  };

  _doHide = () => {
    const { clearOnHide } = this.props;
    this.setState({ show: false });
    if (clearOnHide) {
      this.setState({ input: '' });
    }
  };

  _handleX = () => {
    const { onX } = this.props;
    this._clearInput();
    if (onX) onX();
  };

  _handleBlur = () => {
    const { onBlur, clearOnBlur } = this.props;
    if (onBlur) {
      onBlur();
    }
    if (clearOnBlur) {
      this._clearInput();
    }
  };

  _clearInput = () => {
    this.setState({ input: '' });
    this._onChangeText('');
  };

  _onChangeText = input => {
    const { handleChangeText, handleSearch, handleResults } = this.props;
    this.setState({ input });
    if (handleChangeText) {
      handleChangeText(input);
    }
    if (handleSearch) {
      handleSearch(input);
    } else {
      debounce(() => {
        // use internal search logic (depth first)!
        if (handleResults) {
          const results = this._internalSearch(input);
          handleResults(results);
        }
      }, 500)();
    }
  };

  _internalSearch = input => {
    const { data, allDataOnEmptySearch } = this.props;
    if (input === '') {
      return allDataOnEmptySearch ? data : [];
    }
    return filter(data, item => {
      return this._depthFirstSearch(item, input);
    });
  };

  _depthFirstSearch = (collection, input) => {
    // let's get recursive boi
    let type = typeof collection;
    // base case(s)
    if (type === 'string' || type === 'number' || type === 'boolean') {
      return includes(
        collection.toString().toLowerCase(),
        input.toString().toLowerCase()
      );
    }
    return some(collection, item => this._depthFirstSearch(item, input));
  };

  render = () => {
    const {
      placeholder,
      heightAdjust,
      backgroundColor,
      iconColor,
      textColor,
      selectionColor,
      placeholderTextColor,
      onBack,
      hideBack,
      hideX,
      iOSPadding,
      iOSHideShadow,
      onSubmitEditing,
      onFocus,
      focusOnLayout,
      autoCorrect,
      autoCapitalize,
      keyboardAppearance,
      fontFamily,
      backButton,
      backButtonAccessibilityLabel,
      closeButton,
      closeButtonAccessibilityLabel,
      backCloseSize,
      fontSize,
      editable,
      keyboardType
    } = this.props;
    return (
      <Animated.View
        style={[
          styles.container,
          {
            transform: [
              {
                translateY: this.state.top
              }
            ],
            shadowOpacity: iOSHideShadow ? 0 : 0.7
          }
        ]}>
        {this.state.show && (
          <View style={[styles.navWrapper, { backgroundColor }]}>
            {Platform.OS === 'ios' &&
              iOSPadding && <View style={{ height: 20 }} />}
            <View
              style={[
                styles.nav,
                { height: (Platform.OS === 'ios' ? 52 : 62) + heightAdjust }
              ]}>
              {!hideBack && (
                <TouchableOpacity
                  accessible={true}
                  accessibilityComponentType="button"
                  accessibilityLabel={backButtonAccessibilityLabel}
                  onPress={onBack || this.hide}>
                  {backButton ? (
                    <View
                      style={{ width: backCloseSize, height: backCloseSize }}>
                      {backButton}
                    </View>
                  ) : (
                    <Icon
                      name="arrow-back"
                      size={backCloseSize}
                      style={{
                        color: iconColor,
                        padding: heightAdjust / 2 + 10
                      }}
                    />
                  )}
                </TouchableOpacity>
              )}
              <TextInput
                ref={ref => (this.textInput = ref)}
                onLayout={() => focusOnLayout && this.textInput.focus()}
                style={[
                  styles.input,
                  {
                    fontSize: fontSize,
                    color: textColor,
                    fontFamily: fontFamily,
                    marginLeft: hideBack ? 30 : 0,
                    marginTop: Platform.OS === 'ios' ? heightAdjust / 2 + 10 : 0
                  }
                ]}
                selectionColor={selectionColor}
                onChangeText={input => this._onChangeText(input)}
                onSubmitEditing={() =>
                  onSubmitEditing ? onSubmitEditing() : null}
                onFocus={() => (onFocus ? onFocus() : null)}
                onBlur={this._handleBlur}
                placeholder={placeholder}
                placeholderTextColor={placeholderTextColor}
                value={this.state.input}
                underlineColorAndroid="transparent"
                returnKeyType="search"
                autoCorrect={autoCorrect}
                autoCapitalize={autoCapitalize}
                keyboardType={keyboardType || "default"}
                keyboardAppearance={keyboardAppearance}
                editable={editable}
              />
              <TouchableOpacity
                accessible={true}
                accessibilityComponentType="button"
                accessibilityLabel={closeButtonAccessibilityLabel}
                onPress={
                  hideX || this.state.input === '' ? null : this._handleX
                }>
                {closeButton ? (
                  <View style={{ width: backCloseSize, height: backCloseSize }}>
                    {closeButton}
                  </View>
                ) : (
                  <Icon
                    name={'close'}
                    size={backCloseSize}
                    style={{
                      color:
                        hideX || this.state.input == ''
                          ? backgroundColor
                          : iconColor,
                      padding: heightAdjust / 2 + 10
                    }}
                  />
                )}
              </TouchableOpacity>
            </View>
          </View>
        )}
      </Animated.View>
    );
  };
}

const styles = StyleSheet.create({
  container: {
    flex: 1,
    zIndex: 10,
    position: 'absolute',
    elevation: 2,
    shadowRadius: 5
  },
  navWrapper: {
    width: Dimensions.get('window').width
  },
  nav: {
    ...Platform.select({
      android: {
        borderBottomColor: 'lightgray',
        borderBottomWidth: StyleSheet.hairlineWidth
      }
    }),
    flex: 1,
    flexBasis: 1,
    flexDirection: 'row',
    justifyContent: 'space-around',
    alignItems: 'center'
  },
  input: {
    ...Platform.select({
      ios: { height: 30 },
      android: { height: 50 }
    }),
    width: Dimensions.get('window').width - 120
  }
});
<|endoftext|>


<commit_before>const mysql = require('mysql');
const helper = require('think-helper');
const assert = require('assert');
const Debounce = require('think-debounce');
const thinkInstance = require('think-instance');

const debug = require('debug')('think-mysql');
const debounceInstance = new Debounce();
const QUERY = Symbol('think-mysql-query');
const CONNECTION_LOST = Symbol('think-mysql-connection-lost');

const defaultConfig = {
  port: 3306,
  host: '127.0.0.1',
  user: '',
  password: '',
  database: '',
  connectionLimit: 1,
  logger: console.log.bind(console), /* eslint no-console: ["error", { allow: ["log"] }] */
  logConnect: false,
  logSql: false
};

/**
 * transaction status
 */
const TRANSACTION = {
  start: 1,
  end: 2
};

const TRANSACTIONS = Symbol('transactions');

class ThinkMysql {
  /**
   * @param  {Object} config [connection options]
   */
  constructor(config) {
    config = helper.extend({}, defaultConfig, config);
    this.config = config;
    this.pool = mysql.createPool(helper.omit(config, 'logger,logConnect,logSql'));

    this.pool.on('acquire', connection => {
      debug(`acquire: Connection ${connection.threadId} acquired`);
    });
    this.pool.on('connection', () => {
      debug('connection: A new connection is made within the pool');
    });
    this.pool.on('enqueue', () => {
      debug('enqueue: Waiting for available connection slot');
    });
    this.pool.on('release', connection => {
      debug(`release: Connection ${connection.threadId} released`);
    });

    // log connect
    if (config.logConnect) {
      let connectionPath = '';
      if (config.socketPath) {
        connectionPath = config.socketPath;
      } else {
        connectionPath = `mysql://${config.user}:${config.password}@${config.host}:${config.port || 3306}/${config.database}`;
      }
      config.logger(connectionPath);
    }
  }
  /**
   * get connection
   */
  getConnection(connection) {
    if (connection && !connection[CONNECTION_LOST]) return Promise.resolve(connection);
    return helper.promisify(this.pool.getConnection, this.pool)();
  }
  /**
   * start transaction
   * @param {Object} connection
   */
  startTrans(connection) {
    return this.getConnection(connection).then(connection => {
      if (connection[TRANSACTIONS] === undefined) {
        connection[TRANSACTIONS] = 0;
      }
      connection[TRANSACTIONS]++;
      if (connection[TRANSACTIONS] !== 1) return Promise.resolve();

      return this.query({
        sql: 'START TRANSACTION',
        transaction: TRANSACTION.start,
        debounce: false
      }, connection).then(() => connection);
    });
  }
  /**
   * commit transaction
   * @param {Object} connection
   */
  commit(connection) {
    if (connection && connection[TRANSACTIONS]) {
      connection[TRANSACTIONS]--;
      if (connection[TRANSACTIONS]-- !== 0) return Promise.resolve();
    }
    return this.query({
      sql: 'COMMIT',
      transaction: TRANSACTION.end,
      debounce: false
    }, connection);
  }
  /**
   * rollback transaction
   * @param {Object} connection
   */
  rollback(connection) {
    if (connection && connection[TRANSACTIONS]) {
      connection[TRANSACTIONS]--;
      if (connection[TRANSACTIONS]-- !== 0) return Promise.resolve();
    }
    return this.query({
      sql: 'ROLLBACK',
      transaction: TRANSACTION.end,
      debounce: false
    }, connection);
  }
  /**
   * transaction
   * @param {Function} fn
   * @param {Object} connection
   */
  transaction(fn, connection) {
    assert(helper.isFunction(fn), 'fn must be a function');
    return this.getConnection(connection).then(connection => {
      return this.startTrans(connection).then(() => {
        return fn(connection);
      }).then(data => {
        return this.commit(connection).then(() => data);
      }).catch(err => {
        return this.rollback(connection).then(() => Promise.reject(err));
      });
    });
  }
  /**
   * query data
   */
  [QUERY](sqlOptions, connection, startTime, times = 0) {
    const queryFn = helper.promisify(connection.query, connection);
    return queryFn(sqlOptions).catch(err => err).then(data => {
      this.releaseConnection(connection);

      // if server close connection, then retry it
      if (helper.isError(data) && data.code === 'PROTOCOL_CONNECTION_LOST') {
        connection[CONNECTION_LOST] = true;
        if (times < 3) {
          return this.getConnection().then(connection => {
            return this[QUERY](sqlOptions, connection, startTime, times + 1);
          });
        }
      }
      // log sql
      if (this.config.logSql) {
        const endTime = Date.now();
        this.config.logger(`SQL: ${sqlOptions.sql}, Time: ${endTime - startTime}ms`);
      }
      if (helper.isError(data)) return Promise.reject(data);
      return data;
    });
  }
  /**
   * release connection
   */
  releaseConnection(connection) {
    // if not in transaction, release connection
    if (connection.transaction !== TRANSACTION.start) {
      // connection maybe already released, it will throw an Error
      try {
        connection.release();
      } catch (e) {}
    }
  }
  /**
   * query({
   *  sql: 'SELECT * FROM `books` WHERE `author` = ?',
   *  timeout: 40000, // 40s
   *  values: ['David']
   * })
   * @param {Object} sqlOptions
   * @param {Object} connection
   */
  query(sqlOptions, connection) {
    if (helper.isString(sqlOptions)) {
      sqlOptions = {sql: sqlOptions};
    }
    if (sqlOptions.debounce === undefined) {
      if (this.config.debounce !== undefined) {
        sqlOptions.debounce = this.config.debounce;
      } else {
        sqlOptions.debounce = true;
      }
    }
    const startTime = Date.now();
    if (sqlOptions.debounce) {
      const key = JSON.stringify(sqlOptions);
      return debounceInstance.debounce(key, () => {
        return this.getConnection(connection).then(connection => {
          return this[QUERY](sqlOptions, connection, startTime);
        });
      });
    }
    return this.getConnection(connection).then(connection => {
      // set transaction status to connection
      if (sqlOptions.transaction) {
        if (sqlOptions.transaction === TRANSACTION.start) {
          if (connection.transaction === TRANSACTION.start) return;
        } else if (sqlOptions.transaction === TRANSACTION.end) {
          if (connection.transaction !== TRANSACTION.start) {
            this.releaseConnection(connection);
            return;
          }
        }
        connection.transaction = sqlOptions.transaction;
      }
      return this[QUERY](sqlOptions, connection, startTime);
    });
  }

  /**
   * execute
   * @param  {Array} args []
   * @returns {Promise}
   */
  execute(sqlOptions, connection) {
    if (helper.isString(sqlOptions)) {
      sqlOptions = {sql: sqlOptions};
    }
    sqlOptions.debounce = false;
    return this.query(sqlOptions, connection);
  }
  /**
   * close
   * @returns {Promise}
   */
  close() {
    return helper.promisify(this.pool.end, this.pool)();
  }
}
module.exports = thinkInstance(ThinkMysql);
<commit_msg>add afterConnection method for mysql<commit_after>const mysql = require('mysql');
const helper = require('think-helper');
const assert = require('assert');
const Debounce = require('think-debounce');
const thinkInstance = require('think-instance');

const debug = require('debug')('think-mysql');
const debounceInstance = new Debounce();
const QUERY = Symbol('think-mysql-query');
const CONNECTION_LOST = Symbol('think-mysql-connection-lost');

const defaultConfig = {
  port: 3306,
  host: '127.0.0.1',
  user: '',
  password: '',
  database: '',
  connectionLimit: 1,
  logger: console.log.bind(console), /* eslint no-console: ["error", { allow: ["log"] }] */
  logConnect: false,
  logSql: false
};

/**
 * transaction status
 */
const TRANSACTION = {
  start: 1,
  end: 2
};

const TRANSACTIONS = Symbol('transactions');

class ThinkMysql {
  /**
   * @param  {Object} config [connection options]
   */
  constructor(config) {
    config = helper.extend({}, defaultConfig, config);
    this.config = config;
    this.pool = mysql.createPool(helper.omit(config, 'logger,logConnect,logSql'));

    this.pool.on('acquire', connection => {
      debug(`acquire: Connection ${connection.threadId} acquired`);
    });
    this.pool.on('connection', () => {
      debug('connection: A new connection is made within the pool');
    });
    this.pool.on('enqueue', () => {
      debug('enqueue: Waiting for available connection slot');
    });
    this.pool.on('release', connection => {
      debug(`release: Connection ${connection.threadId} released`);
    });

    // log connect
    if (config.logConnect) {
      let connectionPath = '';
      if (config.socketPath) {
        connectionPath = config.socketPath;
      } else {
        connectionPath = `mysql://${config.user}:${config.password}@${config.host}:${config.port || 3306}/${config.database}`;
      }
      config.logger(connectionPath);
    }
  }
  /**
   * get connection
   */
  getConnection(connection) {
    if (connection && !connection[CONNECTION_LOST]) return Promise.resolve(connection);
    const promise = helper.promisify(this.pool.getConnection, this.pool)();
    if (this.config.afterConnection) {
      return promise.then(connection => {
        return this.config.afterConnection(connection).then(() => connection);
      });
    }
    return promise;
  }
  /**
   * start transaction
   * @param {Object} connection
   */
  startTrans(connection) {
    return this.getConnection(connection).then(connection => {
      if (connection[TRANSACTIONS] === undefined) {
        connection[TRANSACTIONS] = 0;
      }
      connection[TRANSACTIONS]++;
      if (connection[TRANSACTIONS] !== 1) return Promise.resolve();

      return this.query({
        sql: 'START TRANSACTION',
        transaction: TRANSACTION.start,
        debounce: false
      }, connection).then(() => connection);
    });
  }
  /**
   * commit transaction
   * @param {Object} connection
   */
  commit(connection) {
    if (connection && connection[TRANSACTIONS]) {
      connection[TRANSACTIONS]--;
      if (connection[TRANSACTIONS]-- !== 0) return Promise.resolve();
    }
    return this.query({
      sql: 'COMMIT',
      transaction: TRANSACTION.end,
      debounce: false
    }, connection);
  }
  /**
   * rollback transaction
   * @param {Object} connection
   */
  rollback(connection) {
    if (connection && connection[TRANSACTIONS]) {
      connection[TRANSACTIONS]--;
      if (connection[TRANSACTIONS]-- !== 0) return Promise.resolve();
    }
    return this.query({
      sql: 'ROLLBACK',
      transaction: TRANSACTION.end,
      debounce: false
    }, connection);
  }
  /**
   * transaction
   * @param {Function} fn
   * @param {Object} connection
   */
  transaction(fn, connection) {
    assert(helper.isFunction(fn), 'fn must be a function');
    return this.getConnection(connection).then(connection => {
      return this.startTrans(connection).then(() => {
        return fn(connection);
      }).then(data => {
        return this.commit(connection).then(() => data);
      }).catch(err => {
        return this.rollback(connection).then(() => Promise.reject(err));
      });
    });
  }
  /**
   * query data
   */
  [QUERY](sqlOptions, connection, startTime, times = 0) {
    const queryFn = helper.promisify(connection.query, connection);
    return queryFn(sqlOptions).catch(err => err).then(data => {
      this.releaseConnection(connection);

      // if server close connection, then retry it
      if (helper.isError(data) && data.code === 'PROTOCOL_CONNECTION_LOST') {
        connection[CONNECTION_LOST] = true;
        if (times < 3) {
          return this.getConnection().then(connection => {
            return this[QUERY](sqlOptions, connection, startTime, times + 1);
          });
        }
      }
      // log sql
      if (this.config.logSql) {
        const endTime = Date.now();
        this.config.logger(`SQL: ${sqlOptions.sql}, Time: ${endTime - startTime}ms`);
      }
      if (helper.isError(data)) return Promise.reject(data);
      return data;
    });
  }
  /**
   * release connection
   */
  releaseConnection(connection) {
    // if not in transaction, release connection
    if (connection.transaction !== TRANSACTION.start) {
      // connection maybe already released, it will throw an Error
      try {
        connection.release();
      } catch (e) {}
    }
  }
  /**
   * query({
   *  sql: 'SELECT * FROM `books` WHERE `author` = ?',
   *  timeout: 40000, // 40s
   *  values: ['David']
   * })
   * @param {Object} sqlOptions
   * @param {Object} connection
   */
  query(sqlOptions, connection) {
    if (helper.isString(sqlOptions)) {
      sqlOptions = {sql: sqlOptions};
    }
    if (sqlOptions.debounce === undefined) {
      if (this.config.debounce !== undefined) {
        sqlOptions.debounce = this.config.debounce;
      } else {
        sqlOptions.debounce = true;
      }
    }
    const startTime = Date.now();
    if (sqlOptions.debounce) {
      const key = JSON.stringify(sqlOptions);
      return debounceInstance.debounce(key, () => {
        return this.getConnection(connection).then(connection => {
          return this[QUERY](sqlOptions, connection, startTime);
        });
      });
    }
    return this.getConnection(connection).then(connection => {
      // set transaction status to connection
      if (sqlOptions.transaction) {
        if (sqlOptions.transaction === TRANSACTION.start) {
          if (connection.transaction === TRANSACTION.start) return;
        } else if (sqlOptions.transaction === TRANSACTION.end) {
          if (connection.transaction !== TRANSACTION.start) {
            this.releaseConnection(connection);
            return;
          }
        }
        connection.transaction = sqlOptions.transaction;
      }
      return this[QUERY](sqlOptions, connection, startTime);
    });
  }

  /**
   * execute
   * @param  {Array} args []
   * @returns {Promise}
   */
  execute(sqlOptions, connection) {
    if (helper.isString(sqlOptions)) {
      sqlOptions = {sql: sqlOptions};
    }
    sqlOptions.debounce = false;
    return this.query(sqlOptions, connection);
  }
  /**
   * close
   * @returns {Promise}
   */
  close() {
    return helper.promisify(this.pool.end, this.pool)();
  }
}
module.exports = thinkInstance(ThinkMysql);
<|endoftext|>


<commit_before>/* jshint node: true */
'use strict';

module.exports = {
  name: 'ember-plaid'
};
<commit_msg>add link script<commit_after>/* jshint node: true */
'use strict';

module.exports = {
  name: 'ember-plaid',

  contentFor: function(type) {
    if (type === 'body') {
      return '<script src="https://cdn.plaid.com/link/stable/link-initialize.js"></script>';
    }
  },
};
<|endoftext|>


<commit_before>const net = require('net')
const fs = require('fs')
const path = require('path')

module.exports = WFTS

function WFTS (options) {
  this.PORT = options.port || 4000
  this.host = options.host || 'localhost'
  this.file = toPath(options.file)
  this.cmd = options.cmd
}

WFTS.prototype.serve = function serve () {
  const server = net.createServer((socket) => {
    socket.on('end', close)
    socket.on('error', (err) => {
      throw err
    })

    fs.createReadStream(this.file).pipe(socket)
  })

  server.on('error', (err) => {
    console.error(err)
    process.exit(1)
  })

  server.on('close', close)
  server.listen(this.PORT)
}

WFTS.prototype.pull = function pull () {
  const fsw = fs.createWriteStream(this.file, {flags: 'w', defaultEncoding: 'utf8', autoClose: true})

  const socket = net.connect(this.PORT, HOST, () => {
    socket.pipe(fsw).on('finished', () => { console.log('hooo')})
  })

  socket.on('end', () => {
    console.log('transfer complete')
    socket.destroy()
    socket.end()
  })

  socket.on('error', (err) => {
    console.error(err)
    process.exit(1)
  })
}

function toPath(p) {
  if (!/\/d+/.test(p)) return path.join(__dirname, p)
  return p
}

function close () {
  console.log('client disconnected')
  process.exit(0)
}

<commit_msg>Use default opts to createWriteStream<commit_after>const net = require('net')
const fs = require('fs')
const path = require('path')

module.exports = WFTS

function WFTS (options) {
  this.PORT = options.port || 4000
  this.host = options.host || 'localhost'
  this.file = toPath(options.file)
  this.cmd = options.cmd
}

WFTS.prototype.serve = function serve () {
  const server = net.createServer((socket) => {
    socket.on('end', close)
    socket.on('error', (err) => {
      throw err
    })

    fs.createReadStream(this.file).pipe(socket)
  })

  server.on('error', (err) => {
    console.error(err)
    process.exit(1)
  })

  server.on('close', close)
  server.listen(this.PORT)
}

WFTS.prototype.pull = function pull () {
  const fsw = fs.createWriteStream(this.file, 'utf8')

  const socket = net.connect(this.PORT, this.host, () => {
    socket.pipe(fsw).on('finished', () => { console.log('hooo')})
  })

  socket.on('end', () => {
    console.log('transfer complete')
    socket.destroy()
    socket.end()
  })

  socket.on('error', (err) => {
    console.error(err)
    process.exit(1)
  })
}

function toPath(p) {
  if (!/\/d+/.test(p)) return path.join(__dirname, p)
  return p
}

function close () {
  console.log('client disconnected')
  process.exit(0)
}

<|endoftext|>


<commit_before>/**
 * fis.baidu.com
 */
var _ = fis.util;

function upload(receiver, to, data, release, content, file, callback) {
  var subpath = file.subpath;
  data['to'] = to + release;
  fis.util.upload(
      //url, request options, post data, file
      receiver, null, data, content, subpath,
      function(err, res) {
        if (err || res.trim() != '0') {
          callback('upload file [' + subpath + '] to [' + to + '] by receiver [' + receiver + '] error [' + (err || res) + ']');
        } else {
          var time = '[' + fis.log.now(true) + ']';
          process.stdout.write(
              ' - '.green.bold +
              time.grey + ' ' +
              subpath.replace(/^\//, '') +
              ' >> '.yellow.bold +
              to + release +
              '\n'
          );
          callback();
        }
      }
  );
}

module.exports = function(options, modified, total, callback) {
  if (!options.to) {
    throw new Error('options.to is required!');
  } else if (!options.receiver) {
    throw new Error('options.receiver is required!');
  }

  var to = options.to;
  var receiver = options.receiver;
  var data = options.data || {};

  var steps = [];

  modified.forEach(function(file) {
    var reTryCount = options.retry;

    steps.push(function(next) {
      var _upload = arguments.callee;

      upload(receiver, to, data, file.getHashRelease(), file.getContent(), file, function(error) {
        if (error) {
          if (!--reTryCount) {
            throw new Error(error);
          } else {
            _upload();
          }
        } else {
          next();
        }
      });
    });
  });

  _.reduceRight(steps, function(next, current) {
    return function() {
      current(next);
    };
  }, callback)();
};

module.exports.options = {
  // 允许重试两次。
  retry: 2
};
<commit_msg>fix: 兼容用户输入的 to 没有 / 结尾的情况 并允许 retry 设为 null 时关闭重试<commit_after>/**
 * fis.baidu.com
 */
var _ = fis.util;
var path = require('path');

function upload(receiver, to, data, release, content, file, callback) {
  var subpath = file.subpath;
  data['to'] = path.join(to, release);
  fis.util.upload(
      //url, request options, post data, file
      receiver, null, data, content, subpath,
      function(err, res) {
        if (err || res.trim() != '0') {
          callback('upload file [' + subpath + '] to [' + to + '] by receiver [' + receiver + '] error [' + (err || res) + ']');
        } else {
          var time = '[' + fis.log.now(true) + ']';
          process.stdout.write(
              ' - '.green.bold +
              time.grey + ' ' +
              subpath.replace(/^\//, '') +
              ' >> '.yellow.bold +
              to + release +
              '\n'
          );
          callback();
        }
      }
  );
}

module.exports = function(options, modified, total, callback) {
  if (!options.to) {
    throw new Error('options.to is required!');
  } else if (!options.receiver) {
    throw new Error('options.receiver is required!');
  }

  var to = options.to;
  var receiver = options.receiver;
  var data = options.data || {};

  var steps = [];

  modified.forEach(function(file) {
    var reTryCount = options.retry;

    steps.push(function(next) {
      var _upload = arguments.callee;

      upload(receiver, to, data, file.getHashRelease(), file.getContent(), file, function(error) {
        if (error) {
          if (options.retry && !--reTryCount) {
            throw new Error(error);
          } else {
            _upload();
          }
        } else {
          next();
        }
      });
    });
  });

  _.reduceRight(steps, function(next, current) {
    return function() {
      current(next);
    };
  }, callback)();
};

module.exports.options = {
  // 允许重试两次。
  retry: 2
};
<|endoftext|>


<commit_before>'use strict';

/**
 * This module seeds the database with data that should be in the database
 * before the tests should start.
 *
 * @author Sam Verschueren      <sam.verschueren@gmail.com>
 * @since  04 Mar. 2015
 */

// module dependencies
var vm = require('vm'),
    mongoose = require('mongoose'),
    async = require('async'),
    _ = require('lodash'),
    Q = require('q');

module.exports = (function() {

    // The default options
    var DEFAULT_OPTIONS = {
        dropDatabase: true,
        dropCollections: false
    };

    var _this = {
        result: {},
        options: {},
        sandbox: undefined,
        /**
         * The internal method for seeding the database.
         *
         * @param  {Object}   data The data that should be seeded.
         * @param  {Function} done The method that should be called when the seeding is done
         */
        _seed: function(data, done) {
            try {
                // Retrieve all the dependencies
                _.forEach(data._dependencies || {}, function(value, key) {
                    if(this.sandbox[key] !== undefined) {
                        // Do nothing if the dependency is already defined
                        return;
                    }

                    this.sandbox[key] = module.parent.require(value);
                }.bind(this));

                // Remove the dependencies property
                delete data._dependencies;
            }
            catch(e) {
                // Stop execution and return the MODULE_NOT_FOUND error
                return done(e);
            }

            // Iterate over all the data objects
            async.eachSeries(Object.keys(data), function(key, next) {
                _this.result[key] = {};

                var value = data[key];

                try {
                    if(!value._model) {
                        // Throw an error if the model could not be found
                        throw new Error('Please provide a _model property that describes which database model should be used.');
                    }

                    var modelName = value._model;

                    // Remove model and unique properties
                    delete value._model;

                    // retrieve the model depending on the name provided
                    var Model = mongoose.model(modelName);

                    async.series([
                        function(callback) {
                            if(_this.options.dropCollections === true) {
                                // Drop the collection
                                mongoose.connection.db.dropCollection(Model.collection.name, function(err) {
                                    callback();
                                });
                            }
                            else {
                                callback();
                            }
                        },
                        function(callback) {
                            async.eachSeries(Object.keys(value), function(k, innerNext) {
                                var modelData = value[k],
                                    data = _this._unwind(modelData);

                                // Create the model
                                Model.create(data, function(err, result) {
                                    if(err) {
                                        // Do not stop execution if an error occurs
                                        return innerNext(err);
                                    }

                                    _this.result[key][k] = result;

                                    innerNext();
                                });
                            }, callback);
                        }
                    ], next);
                }
                catch(err) {
                    // If the model does not exist, stop the execution
                    return next(err);
                }
            }, function(err) {
                if(err) {
                    // Make sure to not return the result
                    return done(err);
                }

                done(undefined, _this.result);
            });
        },
        /**
         * This method unwinds an object and iterates over every property in the object.
         * It will then parse the value of the property in order to search for references
         * and make a reference to the correct object.
         *
         * @param  {Object} obj The object to parse.
         * @return {Object}     The object with the correct references.
         */
        _unwind: function(obj) {
            return _.mapValues(obj, function(value) {
                return _this._parseValue(obj, value);
            });
        },
        /**
         * This method parses every value. If the value is an object it will unwind
         * that object as well. If the value is a reference (value starting with ->),
         * then it will find the reference to that object.
         *
         * @param  {Object} parent  The object for which the value should be parsed.
         * @param  {*}      value   The value that should be parsed.
         * @return {*}              The parsed value.
         */
        _parseValue: function(parent, value) {
            if(_.isPlainObject(value)) {
                // Unwind the object
                return _this._unwind(value);
            }
            else if(_.isArray(value)) {
                // Iterate over the array
                return _.map(value, function(val) {
                    return _this._parseValue(parent, val);
                });
            }
            else if(_.isString(value) && value.indexOf('=') === 0) {
                // Evaluate the expression
                try {
                    // Assign the object to the _this property
                    var base = {
                       '_this': parent
                    };

                    // Create a new combined context
                    var ctx = vm.createContext(Object.assign(base, _this.sandbox));

                    // Run in the new context
                    return vm.runInContext(value.substr(1).replace(/this\./g, '_this.'), vm.createContext(ctx));
                }
                catch(e) {
                    return value;
                }
            }
            else if(_.isString(value) && value.indexOf('->') === 0) {
                // Find the reference to the object
                return _this._findReference(value.substr(2));
            }

            return value;
        },
        /**
         * This method searches for the _id associated with the object represented
         * by the reference provided.
         *
         * @param  {String} ref The string representation of the reference.
         * @return {String}     The reference to the object.
         */
        _findReference: function(ref) {
            var keys = ref.split('.'),
                key = keys.shift(),
                result = _this.result[key];

            if(!result) {
                // If the result does not exist, return an empty
                throw new TypeError('Could not read property \'' + key + '\' from undefined');
            }

            // Iterate over all the keys and find the property
            while((key = keys.shift())) {
                result = result[key];
            }

            if(_.isObject(result) && !_.isArray(result)) {
                // Test if the result we have is an object. This means the user wants to reference
                // to the _id of the object.
                if(!result._id) {
                    // If no _id property exists, throw a TypeError that the property could not be found
                    throw new TypeError('Could not read property \'_id\' of ' + JSON.stringify(result));
                }

                return result._id;
            }

            return result;
        }
    };

    return {
        /**
         * Start seeding the database.
         *
         * @param  {Object}   data     The data object that should be inserted in the database.
         * @param  {Object}   options  The options object to provide extras.
         * @param  {Function} callback The method that should be called when the seeding is done.
         */
        seed: function(data, options, callback) {
            if(_.isFunction(options)) {
                // Set the correct callback function
                callback = options;
                options = {};
            }

            // Create a deferred object for the promise
            var def = Q.defer();

            // If no callback is provided, use a noop function
            callback = callback || function() {};

            // Clear earlier results and options
            _this.result = {};
            _this.options = {};
            _this.sandbox = vm.createContext();

            // Defaulting the options
            _this.options = _.extend(_.clone(DEFAULT_OPTIONS), options);

            if(_this.options.dropCollections === true && _this.options.dropDatabase === true) {
                // Only one of the two flags can be turned on. If both are true, this means the
                // user set the dropCollections itself and this should have higher priority then
                // the default values.
                _this.options.dropDatabase = false;
            }

            if(_this.options.dropDatabase === true) {
                // Make sure to drop the database first
                mongoose.connection.db.dropDatabase(function(err) {
                    if(err) {
                        // Stop seeding if an error occurred
                        return done(err);
                    }

                    // Start seeding when the database is dropped
                    _this._seed(_.cloneDeep(data), done);
                });
            }
            else {
                // Do not drop the entire database, start seeding
                _this._seed(_.cloneDeep(data), done);
            }

            /**
             * This method will be invoked when the seeding is completed or when something
             * went wrong. This method will then call the callback and rejects or resolves
             * the promise object. This way, users of the library can use both.
             *
             * @param  {*}        err    [description]
             * @param  {Object}   result [description]
             */
            function done(err, result) {
                if(err) {
                    def.reject(err);
                    callback(err);
                    return;
                }

                def.resolve(result);
                callback(undefined, result);
            }

            // Return the promise
            return def.promise;
        }
    };
})();<commit_msg>Added ponyfill for Object.assign<commit_after>'use strict';

/**
 * This module seeds the database with data that should be in the database
 * before the tests should start.
 *
 * @author Sam Verschueren      <sam.verschueren@gmail.com>
 * @since  4 Mar. 2015
 */

// module dependencies
var vm = require('vm'),
    mongoose = require('mongoose'),
    async = require('async'),
    _ = require('lodash'),
    Q = require('q'),
    objectAssign = require('object-assign');

module.exports = (function() {

    // The default options
    var DEFAULT_OPTIONS = {
        dropDatabase: true,
        dropCollections: false
    };

    var _this = {
        result: {},
        options: {},
        sandbox: undefined,
        /**
         * The internal method for seeding the database.
         *
         * @param  {Object}   data The data that should be seeded.
         * @param  {Function} done The method that should be called when the seeding is done
         */
        _seed: function(data, done) {
            try {
                // Retrieve all the dependencies
                _.forEach(data._dependencies || {}, function(value, key) {
                    if(this.sandbox[key] !== undefined) {
                        // Do nothing if the dependency is already defined
                        return;
                    }

                    this.sandbox[key] = module.parent.require(value);
                }.bind(this));

                // Remove the dependencies property
                delete data._dependencies;
            }
            catch(e) {
                // Stop execution and return the MODULE_NOT_FOUND error
                return done(e);
            }

            // Iterate over all the data objects
            async.eachSeries(Object.keys(data), function(key, next) {
                _this.result[key] = {};

                var value = data[key];

                try {
                    if(!value._model) {
                        // Throw an error if the model could not be found
                        throw new Error('Please provide a _model property that describes which database model should be used.');
                    }

                    var modelName = value._model;

                    // Remove model and unique properties
                    delete value._model;

                    // retrieve the model depending on the name provided
                    var Model = mongoose.model(modelName);

                    async.series([
                        function(callback) {
                            if(_this.options.dropCollections === true) {
                                // Drop the collection
                                mongoose.connection.db.dropCollection(Model.collection.name, function(err) {
                                    callback();
                                });
                            }
                            else {
                                callback();
                            }
                        },
                        function(callback) {
                            async.eachSeries(Object.keys(value), function(k, innerNext) {
                                var modelData = value[k],
                                    data = _this._unwind(modelData);

                                // Create the model
                                Model.create(data, function(err, result) {
                                    if(err) {
                                        // Do not stop execution if an error occurs
                                        return innerNext(err);
                                    }

                                    _this.result[key][k] = result;

                                    innerNext();
                                });
                            }, callback);
                        }
                    ], next);
                }
                catch(err) {
                    // If the model does not exist, stop the execution
                    return next(err);
                }
            }, function(err) {
                if(err) {
                    // Make sure to not return the result
                    return done(err);
                }

                done(undefined, _this.result);
            });
        },
        /**
         * This method unwinds an object and iterates over every property in the object.
         * It will then parse the value of the property in order to search for references
         * and make a reference to the correct object.
         *
         * @param  {Object} obj The object to parse.
         * @return {Object}     The object with the correct references.
         */
        _unwind: function(obj) {
            return _.mapValues(obj, function(value) {
                return _this._parseValue(obj, value);
            });
        },
        /**
         * This method parses every value. If the value is an object it will unwind
         * that object as well. If the value is a reference (value starting with ->),
         * then it will find the reference to that object.
         *
         * @param  {Object} parent  The object for which the value should be parsed.
         * @param  {*}      value   The value that should be parsed.
         * @return {*}              The parsed value.
         */
        _parseValue: function(parent, value) {
            if(_.isPlainObject(value)) {
                // Unwind the object
                return _this._unwind(value);
            }
            else if(_.isArray(value)) {
                // Iterate over the array
                return _.map(value, function(val) {
                    return _this._parseValue(parent, val);
                });
            }
            else if(_.isString(value) && value.indexOf('=') === 0) {
                // Evaluate the expression
                try {
                    // Assign the object to the _this property
                    var base = {
                       '_this': parent
                    };

                    // Create a new combined context
                    var ctx = vm.createContext(objectAssign(base, _this.sandbox));

                    // Run in the new context
                    return vm.runInContext(value.substr(1).replace(/this\./g, '_this.'), vm.createContext(ctx));
                }
                catch(e) {
                    return value;
                }
            }
            else if(_.isString(value) && value.indexOf('->') === 0) {
                // Find the reference to the object
                return _this._findReference(value.substr(2));
            }

            return value;
        },
        /**
         * This method searches for the _id associated with the object represented
         * by the reference provided.
         *
         * @param  {String} ref The string representation of the reference.
         * @return {String}     The reference to the object.
         */
        _findReference: function(ref) {
            var keys = ref.split('.'),
                key = keys.shift(),
                result = _this.result[key];

            if(!result) {
                // If the result does not exist, return an empty
                throw new TypeError('Could not read property \'' + key + '\' from undefined');
            }

            // Iterate over all the keys and find the property
            while((key = keys.shift())) {
                result = result[key];
            }

            if(_.isObject(result) && !_.isArray(result)) {
                // Test if the result we have is an object. This means the user wants to reference
                // to the _id of the object.
                if(!result._id) {
                    // If no _id property exists, throw a TypeError that the property could not be found
                    throw new TypeError('Could not read property \'_id\' of ' + JSON.stringify(result));
                }

                return result._id;
            }

            return result;
        }
    };

    return {
        /**
         * Start seeding the database.
         *
         * @param  {Object}   data     The data object that should be inserted in the database.
         * @param  {Object}   options  The options object to provide extras.
         * @param  {Function} callback The method that should be called when the seeding is done.
         */
        seed: function(data, options, callback) {
            if(_.isFunction(options)) {
                // Set the correct callback function
                callback = options;
                options = {};
            }

            // Create a deferred object for the promise
            var def = Q.defer();

            // If no callback is provided, use a noop function
            callback = callback || function() {};

            // Clear earlier results and options
            _this.result = {};
            _this.options = {};
            _this.sandbox = vm.createContext();

            // Defaulting the options
            _this.options = _.extend(_.clone(DEFAULT_OPTIONS), options);

            if(_this.options.dropCollections === true && _this.options.dropDatabase === true) {
                // Only one of the two flags can be turned on. If both are true, this means the
                // user set the dropCollections itself and this should have higher priority then
                // the default values.
                _this.options.dropDatabase = false;
            }

            if(_this.options.dropDatabase === true) {
                // Make sure to drop the database first
                mongoose.connection.db.dropDatabase(function(err) {
                    if(err) {
                        // Stop seeding if an error occurred
                        return done(err);
                    }

                    // Start seeding when the database is dropped
                    _this._seed(_.cloneDeep(data), done);
                });
            }
            else {
                // Do not drop the entire database, start seeding
                _this._seed(_.cloneDeep(data), done);
            }

            /**
             * This method will be invoked when the seeding is completed or when something
             * went wrong. This method will then call the callback and rejects or resolves
             * the promise object. This way, users of the library can use both.
             *
             * @param  {*}        err    [description]
             * @param  {Object}   result [description]
             */
            function done(err, result) {
                if(err) {
                    def.reject(err);
                    callback(err);
                    return;
                }

                def.resolve(result);
                callback(undefined, result);
            }

            // Return the promise
            return def.promise;
        }
    };
})();<|endoftext|>


<commit_before>
function updateQueryStringParameter(uri, key, value) {
  var re = new RegExp("([?&])" + key + "=.*?(&|$)", "i");
  var separator = uri.indexOf('?') !== -1 ? "&" : "?";
  if (uri.match(re)) {
    return uri.replace(re, '$1' + key + "=" + value + '$2');
  }
  else {
    return uri + separator + key + "=" + value;
  }
}

var QueryString = function () {
  // This function is anonymous, is executed immediately and
  // the return value is assigned to QueryString!
  var query_string = {};
  var query = window.location.search.substring(1);
  var vars = query.split("&");
  for (var i=0;i<vars.length;i++) {
    var pair = vars[i].split("=");
        // If first entry with this name
    if (typeof query_string[pair[0]] === "undefined") {
      query_string[pair[0]] = decodeURIComponent(pair[1]);
        // If second entry with this name
    } else if (typeof query_string[pair[0]] === "string") {
      var arr = [ query_string[pair[0]],decodeURIComponent(pair[1]) ];
      query_string[pair[0]] = arr;
        // If third or later entry with this name
    } else {
      query_string[pair[0]].push(decodeURIComponent(pair[1]));
    }
  }
    return query_string;
}();

function isNumber(n) {
  return !isNaN(parseFloat(n)) && isFinite(n);
}

var defaultColors = [
  '#113F8C',
  '#01A4A4',
  '#00A1CB',
  '#61AE24',
  '#D0D102',
  '#32742C',
  '#D70060',
  '#E54028',
  '#F18D05'
];

var channel = QueryString.channel || 'pubnub-sensor-network';
var subscribe_key = QueryString.subscribe_key || 'sub-c-5f1b7c8e-fbee-11e3-aa40-02ee2ddab7fe';

var builder = function(params) {

  var self = this;

  self.cols = [];
  self.labels = {};
  self.colors = {};

  self.refresh = function(params) {

    var params = params || {};

    self.type = params.type || self.type || 'spline';
    self.limit = params.limit || self.limit || 5;
    self.xlabel = params.xlabel || self.xlabel || '';
    self.ylabel = params.ylabel || self.ylabel || '';

    self.rate = params.rate || self.rate || 1000;
    self.duration = params.duration || self.duration || 250;

    if(typeof self.history == "undefined") {
      self.history = false;
    }

    if(typeof params.history !== "undefined") {
      self.history = params.history;
    }

    if(typeof self.xgrid == "undefined") {
      self.xgrid = false;
    }

    if(typeof params.xgrid !== "undefined") {
      self.xgrid = params.xgrid;
    }

    if(typeof self.ygrid == "undefined") {
      self.ygrid = false;
    }

    if(typeof params.ygrid !== "undefined") {
      self.ygrid = params.ygrid;
    }

    if(typeof self.points == "undefined") {
      self.points = true;
    }

    if(typeof params.points !== "undefined") {
      self.points = params.points;
    }

    if(typeof self.tooltips == "undefined") {
      self.tooltips = true;
    }

    if(typeof params.tooltips !== "undefined") {
      self.tooltips = params.tooltips;
    }

    self.flow = false;

    if(self.type == "spline" ||
      self.type == "area" ||
      self.type == "area-spline" ||
      self.type == "step" ||
      self.type == "area-step" ||
      self.type == "scatter") {

      self.flow = true;

      $('#limit-row, #points-row, #xgrid-row, #ygrid-row').show();

    } else {
      $('#limit-row, #points-row, #xgrid-row, #ygrid-row').hide();
    }

    self.chart = eon.chart({
      pubnub: self.pubnub,
      channel: channel,
      history: self.history,
      flow: self.flow,
      rate: self.rate,
      limit: self.limit,
      generate: {
        bindto: '#chart',
        data: {
          x: self.x,
          type: self.type,
          colors: self.colors
        },
        transition: {
          duration: self.duration
        },
        axis: {
          x: {
            label: self.xlabel,
          },
          y: {
            label: self.ylabel
          }
        },
        grid: {
          x: {
            show: self.xgrid
          },
          y: {
            show: self.ygrid
          }
        },
        tooltip: {
          show: self.tooltips
        },
        point: {
          show: self.points
        }
      },
      transform: function(message) {

        var message = eon.c.flatten(message);
        var o = {};

        for(index in message) {
          if(self.cols.indexOf(index) > -1){
            o[self.labels[index] || index] = message[index];
          }
        }

        return {
          eon: o
        };

      }
    });

    self.pedit.subscribe({
      channel: channel,
      message: function(data, a, b) {

        var data = eon.c.flatten(data);

        for(var key in data) {

          var $row = $('[data-key="' + key + '"]');
          var value = data[key];

          if(!isNaN(value)) {

            if($row.length) {

              $row.find('.val').text(value)

            } else {

              self.cols.push(key);

              var color = defaultColors[$('tr').length % defaultColors.length];

              var $row = $('\

 \
                  ' + key + '	 \
                  ' + value + '	 \
                   \
                    <dciv class="input-group colorpick" data-key="' + key + '"> \
                        <input type="text" value="' + color + '" class="form-control" /> \
                         \

 \
                  	 \
                   \
                  <input type="checkbox" class="toggle" checked data-toggle="toggle"> \
                  	 \

');

              var picker = $row.find('.colorpick').colorpicker();

              self.colors[key] = color;
              picker.on('changeColor.colorpicker', function(event){

                self.colors[$(this).closest('tr').attr('data-key')] = event.color.toHex();
                self.embed();

              });

              $row.find('#key-edit').editable({
                  unsavedclass: null,
                  success: function(response, newValue) {

                    var thisKey = $(this).closest('tr').attr('data-key');

                    self.labels[thisKey] = newValue;

                    // colors map to labels in c3
                    self.colors[newValue] = self.colors[thisKey];
                    delete self.colors[thisKey];

                    self.refresh();

                  }
              });

              $row.find('.toggle').bootstrapToggle('on');

              $row.find('.toggle').change(function() {

                var thisKey = $(this).closest('tr').attr('data-key');
                var isChecked = $(this).prop('checked');

                if(typeof (isChecked) !== "undefined") {

                  if(isChecked){

                    self.cols.push(thisKey);
                    self.embed();

                  } else {

                    for(var i in self.cols) {

                      if(self.cols[i] == thisKey) {
                        self.cols.splice(i, 1);
                        self.refresh();
                      }

                    }

                  }

                }

              });

              $('#kvs').append($row);
              self.embed();

            }

          }

        }

      }
    });

    self.embed();

  }

  self.embed = function() {

    var embedsrc = '' +
      '


<commit_before>'use strict';
var svnode = function() {
  var svn = require('svn-interface');

  svn.status('', {}, function(err, res){
    console.log(res.status.target.entry.map(function(entry){
      return entry['wc-status']._attribute.item + ' - ' + entry._attribute.path;
    }));
  });
};

module.export = svnode;
<commit_msg>:whale2: use modules in main file<commit_after>'use strict';
var svnode = {
  status: require('./lib/status')
};

svnode.status();
<|endoftext|>


<commit_before>const async = require('asyncawait/async');
const await = require('asyncawait/await');
const bodyParser = require('body-parser');
const express = require('express');
const MongoClient = require('mongodb').MongoClient;
const path = require('path');
const spawn = require('child_process').spawn;
const url = 'mongodb://155.246.39.17:27017/orbitalFederates';
const build = {
    GROUND: function buildGround(ground, playerId, basePos) {
        return `${playerId + 1}.GroundSta@SUR${basePos},${ground.components.join(',')}`;
    },
    SAT: function (sat, playerId, satPos) {
        if (sat.components <= 2) {
            return `${playerId + 1}.SmallSat@MEO${satPos},${sat.components.join(',')}`;
        } else if (sat.components <= 4) {
            return `${playerId + 1}.MediumSat@MEO${satPos},${sat.components.join(',')}`;
        } else {
            return `${playerId + 1}.LargeSat@MEO${satPos},${sat.components.join(',')}`;
        }
    }
};

MongoClient.connect(url, async(function (err, db) {
    if (err) return console.error('Unable to connect to the mongoDB server. Error:', err);
    console.log('Connection established to', url);
    let app = express();
    let curProcessCount = 0;
    let maxProcessCount = 20;
    let waitingProcess = [];

    function processRun(callback) {
        if (curProcessCount >= maxProcessCount) return waitingProcess.push(callback);

        curProcessCount += 1;
        callback();
    }

    function processClose() {
        curProcessCount -= 1;

        while (curProcessCount < maxProcessCount && waitingProcess.length > 0) {
            curProcessCount += 1;
            (waitingProcess.shift())();
        }
    }

    app.use(bodyParser.json());
    app.use(express.static('public'));

    const runOfs = async(function (args, config) {
        return new Promise((resolve, reject) => {
            processRun(() => {
                let process = spawn('python', args, { cwd: path.join(__dirname, 'ofspy', 'bin') });
                let lines = [];
                let result = '';

                process.stdout.on('data', function (data) {
                    // TODO: Make sure to store seed, locations, algorithms, and design.
                    result += data.toString();
                });

                process.stderr.on('data', (data) => {
                    console.log(`stderr: ${data}`);
                });

                process.on('close', (code) => {
                    //console.log('Connection closed');
                    resolve({
                        results: result,
                        config: config
                    });

                    processClose();
                });
            });
        });
    });

    const runSim = async(function (federateIds, count, loc, turns = 24, oAlg = 'd6,a,1', fAlg = 'n') {
        let designCollection = db.collection('designs');
        let federateCollection = db.collection('federates');
        let resultsCollection = db.collection('results');
        let sims = [];
        // Caches:
        let federatesCache = {};
        let designsCache = {};

        function getBasePos(playerId) {
            // Evenly spaces the players:
            return Math.floor(playerId / federateIds.length * 6) + 1;
        }

        const fetchFederate = async(function (federateId) {
            if (!federatesCache[federateId]) federatesCache[federateId] = await(federateCollection.findOne({ federateId: federateId }));

            return federatesCache[federateId];
        });

        const fetchDesign = async(function (designId) {
            if (!designsCache[designId]) designsCache[designId] = await(designCollection.findOne({ designId: designId }));

            return designsCache[designId];
        });

        // TODO: Generate locs before running seeds
        // Build sats:
        let playerId = 0;
        let designArgs = [];
        if (loc == null) loc = [];
        for (const federateId of federateIds) {
            const federate = await(fetchFederate(federateId));
            let designNum = 0;
            let designIndex = 0;
            if (loc[playerId] == null) loc[playerId] = [];

            for (const designId of federate.designIds) {
                const design = await(fetchDesign(designId));

                if (design.objectType === 'GROUND') {
                    if (loc[playerId][designIndex] == null) loc[playerId][designIndex] = getBasePos(playerId);

                    designArgs.push(build[design.objectType](design, playerId, loc[playerId][designIndex]));
                } else {
                    if (loc[playerId][designIndex] == null) loc[playerId][designIndex] = getBasePos(playerId) + designNum;

                    designArgs.push(build[design.objectType](design, playerId, loc[playerId][designIndex]));
                    designNum += 1;
                }
                designIndex += 1;
            }
            playerId += 1;
        }

        let matchConfig = {
            'config.federateIds': federateIds,
            'config.loc': loc,
            'config.turns': turns,
            'config.seed': { $gte: 0, $lt: count },
            'config.o': oAlg,
            'config.f': fAlg
        };

        let seeds = await(resultsCollection.find(matchConfig).project({ _id: 0, "config.seed": 1 }).toArray()).reduce((o, s) => {
            o[s.config.seed] = true; return o;
        }, {});

        for (let seed = 0; seed < count; seed += 1) {
            if (seeds[seed]) continue; // If all done, skip

            let args = [path.join(__dirname, 'ofspy', 'bin', 'ofs.py'), ...designArgs];

            // Run sim:
            let runArgs = args.concat([
                '-d', `${turns}`,
                '-s', `${seed}`,
                '-o', `${oAlg}`,
                '-f', `${fAlg}`
            ]);

            let config = {
                federateIds: federateIds,
                loc: loc,
                turns: turns,
                seed: seed,
                o: oAlg,
                f: fAlg
            };

            //console.log(args);
            sims.push(runOfs(runArgs, config));
        }

        // Wait for them to complete before returning
        let results = await(sims).map((result, seed) => {
            result.config.startCash = [];

            // Parse results:
            return result.results.match(/[^\r\n]+/gi).reduce((res, fed) => {
                cash = fed.split(':');

                res.config.startCash.push(parseFloat(cash[0]));
                res.results.endCash.push(parseFloat(cash[1]));

                return res;
            }, {
                config: result.config,
                results: {
                    endCash: []
                }
            });
        });

        if (results.length > 0) {
            await(resultsCollection.insert(results));
            //console.log("new", results);
        }

        console.log(federateIds);
        return await(resultsCollection.find(matchConfig).toArray());
    });

    app.post('/runsim', async(function (req, res) {
        res.json(await(runSim(req.body.federateIds, req.body.count, req.body.loc, req.body.turns, req.body.o, req.body.f)));
    }));

    app.get('/results/clear', async(function (req, res) {
        let resultsCollection = db.collection('results');
        resultsCollection.drop();
        resultsCollection.createIndex({ "config.federateIds": 1 });
        resultsCollection.createIndex({ "config.loc": 1 });
        resultsCollection.createIndex({ "config.o": 1 });
        resultsCollection.createIndex({ "config.f": 1 });
        resultsCollection.createIndex({ "config.turns": 1 });
        resultsCollection.createIndex({ "config.seed": 1 });
        resultsCollection.createIndex({ "results.endCash": 1 });

        res.json("\"success\"");
    }));

    app.post('/mean', async(function (req, res) {
        let resultsCollection = db.collection('results');
        let match = {};

        for (const field of Object.keys(req.body.config)) {
            match['config.' + field] = req.body.config[field];
        }

        let results = await(resultsCollection.find(match).project({ _id: 0, "config.federateIds": 1, "results.endCash": 1 }).toArray());

        res.json(results.reduce((result, res, index, array) => {
            if (result.federateIds == null) {
                result.federateIds = res.config.federateIds;
                result.endCash = new Array(result.federateIds.length);

                for (let i = 0; i < res.config.federateIds.length; i += 1) {
                    result.endCash[i] = res.results.endCash[i] / array.length;
                }
            } else {
                for (let i = 0; i < res.config.federateIds.length; i += 1) {
                    result.endCash[i] += res.results.endCash[i] / array.length;
                }
            }

            return result;
        }, {}));
    }));

    app.listen(3000, function () {
        console.log('Example app listening on port 3000!')
    });
}));<commit_msg>Add seed count to mean api call<commit_after>const async = require('asyncawait/async');
const await = require('asyncawait/await');
const bodyParser = require('body-parser');
const express = require('express');
const MongoClient = require('mongodb').MongoClient;
const path = require('path');
const spawn = require('child_process').spawn;
const url = 'mongodb://155.246.39.17:27017/orbitalFederates';
const build = {
    GROUND: function buildGround(ground, playerId, basePos) {
        return `${playerId + 1}.GroundSta@SUR${basePos},${ground.components.join(',')}`;
    },
    SAT: function (sat, playerId, satPos) {
        if (sat.components <= 2) {
            return `${playerId + 1}.SmallSat@MEO${satPos},${sat.components.join(',')}`;
        } else if (sat.components <= 4) {
            return `${playerId + 1}.MediumSat@MEO${satPos},${sat.components.join(',')}`;
        } else {
            return `${playerId + 1}.LargeSat@MEO${satPos},${sat.components.join(',')}`;
        }
    }
};

MongoClient.connect(url, async(function (err, db) {
    if (err) return console.error('Unable to connect to the mongoDB server. Error:', err);
    console.log('Connection established to', url);
    let app = express();
    let curProcessCount = 0;
    let maxProcessCount = 20;
    let waitingProcess = [];

    function processRun(callback) {
        if (curProcessCount >= maxProcessCount) return waitingProcess.push(callback);

        curProcessCount += 1;
        callback();
    }

    function processClose() {
        curProcessCount -= 1;

        while (curProcessCount < maxProcessCount && waitingProcess.length > 0) {
            curProcessCount += 1;
            (waitingProcess.shift())();
        }
    }

    app.use(bodyParser.json());
    app.use(express.static('public'));

    const runOfs = async(function (args, config) {
        return new Promise((resolve, reject) => {
            processRun(() => {
                let process = spawn('python', args, { cwd: path.join(__dirname, 'ofspy', 'bin') });
                let lines = [];
                let result = '';

                process.stdout.on('data', function (data) {
                    // TODO: Make sure to store seed, locations, algorithms, and design.
                    result += data.toString();
                });

                process.stderr.on('data', (data) => {
                    console.log(`stderr: ${data}`);
                });

                process.on('close', (code) => {
                    //console.log('Connection closed');
                    resolve({
                        results: result,
                        config: config
                    });

                    processClose();
                });
            });
        });
    });

    const runSim = async(function (federateIds, count, loc, turns = 24, oAlg = 'd6,a,1', fAlg = 'n') {
        let designCollection = db.collection('designs');
        let federateCollection = db.collection('federates');
        let resultsCollection = db.collection('results');
        let sims = [];
        // Caches:
        let federatesCache = {};
        let designsCache = {};

        function getBasePos(playerId) {
            // Evenly spaces the players:
            return Math.floor(playerId / federateIds.length * 6) + 1;
        }

        const fetchFederate = async(function (federateId) {
            if (!federatesCache[federateId]) federatesCache[federateId] = await(federateCollection.findOne({ federateId: federateId }));

            return federatesCache[federateId];
        });

        const fetchDesign = async(function (designId) {
            if (!designsCache[designId]) designsCache[designId] = await(designCollection.findOne({ designId: designId }));

            return designsCache[designId];
        });

        // TODO: Generate locs before running seeds
        // Build sats:
        let playerId = 0;
        let designArgs = [];
        if (loc == null) loc = [];
        for (const federateId of federateIds) {
            const federate = await(fetchFederate(federateId));
            let designNum = 0;
            let designIndex = 0;
            if (loc[playerId] == null) loc[playerId] = [];

            for (const designId of federate.designIds) {
                const design = await(fetchDesign(designId));

                if (design.objectType === 'GROUND') {
                    if (loc[playerId][designIndex] == null) loc[playerId][designIndex] = getBasePos(playerId);

                    designArgs.push(build[design.objectType](design, playerId, loc[playerId][designIndex]));
                } else {
                    if (loc[playerId][designIndex] == null) loc[playerId][designIndex] = getBasePos(playerId) + designNum;

                    designArgs.push(build[design.objectType](design, playerId, loc[playerId][designIndex]));
                    designNum += 1;
                }
                designIndex += 1;
            }
            playerId += 1;
        }

        let matchConfig = {
            'config.federateIds': federateIds,
            'config.loc': loc,
            'config.turns': turns,
            'config.seed': { $gte: 0, $lt: count },
            'config.o': oAlg,
            'config.f': fAlg
        };

        let seeds = await(resultsCollection.find(matchConfig).project({ _id: 0, "config.seed": 1 }).toArray()).reduce((o, s) => {
            o[s.config.seed] = true; return o;
        }, {});

        for (let seed = 0; seed < count; seed += 1) {
            if (seeds[seed]) continue; // If all done, skip

            let args = [path.join(__dirname, 'ofspy', 'bin', 'ofs.py'), ...designArgs];

            // Run sim:
            let runArgs = args.concat([
                '-d', `${turns}`,
                '-s', `${seed}`,
                '-o', `${oAlg}`,
                '-f', `${fAlg}`
            ]);

            let config = {
                federateIds: federateIds,
                loc: loc,
                turns: turns,
                seed: seed,
                o: oAlg,
                f: fAlg
            };

            //console.log(args);
            sims.push(runOfs(runArgs, config));
        }

        // Wait for them to complete before returning
        let results = await(sims).map((result, seed) => {
            result.config.startCash = [];

            // Parse results:
            return result.results.match(/[^\r\n]+/gi).reduce((res, fed) => {
                cash = fed.split(':');

                res.config.startCash.push(parseFloat(cash[0]));
                res.results.endCash.push(parseFloat(cash[1]));

                return res;
            }, {
                config: result.config,
                results: {
                    endCash: []
                }
            });
        });

        if (results.length > 0) {
            await(resultsCollection.insert(results));
            //console.log("new", results);
        }

        console.log(federateIds);
        return await(resultsCollection.find(matchConfig).toArray());
    });

    app.post('/runsim', async(function (req, res) {
        res.json(await(runSim(req.body.federateIds, req.body.count, req.body.loc, req.body.turns, req.body.o, req.body.f)));
    }));

    app.get('/results/clear', async(function (req, res) {
        let resultsCollection = db.collection('results');
        resultsCollection.drop();
        resultsCollection.createIndex({ "config.federateIds": 1 });
        resultsCollection.createIndex({ "config.loc": 1 });
        resultsCollection.createIndex({ "config.o": 1 });
        resultsCollection.createIndex({ "config.f": 1 });
        resultsCollection.createIndex({ "config.turns": 1 });
        resultsCollection.createIndex({ "config.seed": 1 });
        resultsCollection.createIndex({ "results.endCash": 1 });

        res.json("\"success\"");
    }));

    app.post('/mean', async(function (req, res) {
        let resultsCollection = db.collection('results');
        let match = {};

        for (const field of Object.keys(req.body.config)) {
            match['config.' + field] = req.body.config[field];
        }

        let results = await(resultsCollection.find(match).project({ _id: 0, "config.federateIds": 1, "results.endCash": 1 }).toArray());

        res.json(results.reduce((result, res, index, array) => {
            if (result.federateIds == null) {
                result.federateIds = res.config.federateIds;
                result.endCash = new Array(result.federateIds.length);

                for (let i = 0; i < res.config.federateIds.length; i += 1) {
                    result.endCash[i] = res.results.endCash[i] / array.length;
                }
            } else {
                for (let i = 0; i < res.config.federateIds.length; i += 1) {
                    result.endCash[i] += res.results.endCash[i] / array.length;
                }
            }

            return result;
        }, { seeds: results.length }));
    }));

    app.listen(3000, function () {
        console.log('Example app listening on port 3000!')
    });
}));<|endoftext|>


<commit_before>'use strict';

var query = require('./js/query.js');
var express = require('express');
var app = express();

app.use(express.json());

app.get('/', function(req, res){
  res.sendfile(__dirname + '/public/index.html');
});

app.get('/data', function(req, res) {
  query("SELECT login FROM users WHERE id = 1", function(data) {
    res.json(data);
  });
});

app.get('/login/:login/:password', function(req, res) {
  query("SELECT * FROM users WHERE login = '" + req.params.login + "' AND password = '" + req.params.password + "'", function(data) {
    res.json(data);
  });
});

app.post('/register', function(req, res) {
  query("SELECT * FROM users WHERE login = '" + req.body.login + "' AND password = '" + req.body.password + "'", function(data) {
    if(data.length != 0) {
      res.json({error : 1});
      return;
    }
    query("INSERT INTO users (login, password, email, name, surname, patronymic) VALUES ('" + req.body.login + "', '" + req.body.password + "', '" + req.body.email + "', '" + req.body.name + "', '" + req.body.surname + "', '" + req.body.patronymic + "');", function(data) {
      res.json({success : 1});
    });
  });
});

app.use(express.static(__dirname + '/public'));

app.listen(process.env.PORT || 8888);<commit_msg>Favicon fix<commit_after>'use strict';

var query = require('./js/query.js');
var express = require('express');
var app = express();

app.use(express.json())
  .use(express.favicon(__dirname + '/public/images/favicon.ico'))
  .get('/', function(req, res) {
    res.sendfile(__dirname + '/public/index.html');
  })
  .get('/data', function(req, res) {
    query("SELECT login FROM users WHERE id = 1", function(data) {
      res.json(data);
    });
  })
  .get('/login/:login/:password', function(req, res) {
    query("SELECT * FROM users WHERE login = '" + req.params.login + "' AND password = '" + req.params.password + "'", function(data) {
      res.json(data);
    });
  })
  .post('/register', function(req, res) {
    query("SELECT * FROM users WHERE login = '" + req.body.login + "' AND password = '" + req.body.password + "'", function(data) {
      if(data.length != 0) {
        res.json({error : 1});
        return;
      }
      query("INSERT INTO users (login, password, email, name, surname, patronymic) VALUES ('" + req.body.login + "', '" + req.body.password + "', '" + req.body.email + "', '" + req.body.name + "', '" + req.body.surname + "', '" + req.body.patronymic + "');", function(data) {
        res.json({success : 1});
      });
    });
  })
  .use(express.static(__dirname + '/public'))
  .listen(process.env.PORT || 8888);<|endoftext|>


<commit_before>var path = require('path');
var fs   = require('fs');

function EmberCLISimpleAuth(project) {
  this.project = project;
  this.name    = 'Ember CLI Simple Auth';
}

function unwatchedTree(dir) {
  return {
    read:    function() { return dir; },
    cleanup: function() { }
  };
}

EmberCLISimpleAuth.prototype.treeFor = function included(name) {
  var treePath =  path.join('node_modules/ember-cli-simple-auth', name + '-addon');

  if (fs.existsSync(treePath)) {
    return unwatchedTree(treePath);
  }
};

EmberCLISimpleAuth.prototype.included = function included(app) {
  this.app = app;

  this.app.import('vendor/ember-simple-auth/simple-auth.amd.js', {
    'simple-auth/authenticators/base':                    ['default'],
    'simple-auth/authorizers/base':                       ['default'],
    'simple-auth/mixins/application-route-mixin':         ['default'],
    'simple-auth/mixins/authenticated-route-mixin':       ['default'],
    'simple-auth/mixins/authentication-controller-mixin': ['default'],
    'simple-auth/mixins/login-controller-mixin':          ['default'],
    'simple-auth/stores/base':                            ['default'],
    'simple-auth/stores/ephemeral':                       ['default'],
    'simple-auth/stores/local-storage':                   ['default'],
    'simple-auth/configuration':                          ['default'],
    'simple-auth/initializer':                            ['default']
  });
};

module.exports = EmberCLISimpleAuth;<commit_msg>newline<commit_after>var path = require('path');
var fs   = require('fs');

function EmberCLISimpleAuth(project) {
  this.project = project;
  this.name    = 'Ember CLI Simple Auth';
}

function unwatchedTree(dir) {
  return {
    read:    function() { return dir; },
    cleanup: function() { }
  };
}

EmberCLISimpleAuth.prototype.treeFor = function included(name) {
  var treePath =  path.join('node_modules/ember-cli-simple-auth', name + '-addon');

  if (fs.existsSync(treePath)) {
    return unwatchedTree(treePath);
  }
};

EmberCLISimpleAuth.prototype.included = function included(app) {
  this.app = app;

  this.app.import('vendor/ember-simple-auth/simple-auth.amd.js', {
    'simple-auth/authenticators/base':                    ['default'],
    'simple-auth/authorizers/base':                       ['default'],
    'simple-auth/mixins/application-route-mixin':         ['default'],
    'simple-auth/mixins/authenticated-route-mixin':       ['default'],
    'simple-auth/mixins/authentication-controller-mixin': ['default'],
    'simple-auth/mixins/login-controller-mixin':          ['default'],
    'simple-auth/stores/base':                            ['default'],
    'simple-auth/stores/ephemeral':                       ['default'],
    'simple-auth/stores/local-storage':                   ['default'],
    'simple-auth/configuration':                          ['default'],
    'simple-auth/initializer':                            ['default']
  });
};

module.exports = EmberCLISimpleAuth;
<|endoftext|>