<commit_before>import React, { Component, PropTypes } from 'react';
import CSSTransitionGroup from 'react-addons-css-transition-group';
import cx from 'classnames';

import Icon from '../../Icon/Icon';
import noop from '../../../utils/noop';
import css from './Select.css';

export default class Select extends Component {
  static propTypes = {
    onFocus: PropTypes.func,
    onBlur: PropTypes.func,
    onChange: PropTypes.func,
    name: PropTypes.string,
    id: PropTypes.string,
    required: PropTypes.bool,
    className: PropTypes.string,
    hasError: PropTypes.bool,
    multiple: PropTypes.bool,
    children: PropTypes.node.isRequired,
    value: PropTypes.oneOfType([
      PropTypes.string,
      PropTypes.array,
    ]),
    error: PropTypes.string,
    priority: PropTypes.oneOf(['high']),
  };

  static defaultProps = {
    onChange: noop,
    onFocus: noop,
    onBlur: noop,
  };

  state = {
    hasFocus: false,
  }

  focus = () => {
    this.select.focus();
    this.handleFocus();
  }

  blur = () => {
    this.select.blur();
    this.handleBlur();
  }

  handleFocus = () => {
    const { onFocus } = this.props;
    this.setState({ hasFocus: true }, onFocus);
  }

  handleBlur = () => {
    const { onBlur } = this.props;
    this.setState({ hasFocus: false }, onBlur);
  }

  handleChange = (e) => {
    const { onChange, name, multiple } = this.props;
    const value = multiple
      ? [].filter.call(this.select.options, o => o.selected).map(o => o.value)
      : e.target.value;

    onChange(e, name, value);
  }

  render() {
    const { hasFocus } = this.state;

    const {
      name,
      id,
      required,
      error,
      className,
      multiple,
      value,
      children,
      priority,
      ...rest,
    } = this.props;

    const classes = cx(
      css.select,
      hasFocus ? css.focus : null,
      error ? css.error : null,
      css[priority],
    );

    return (
      <div className={ cx(css.wrapper, className) }>
        <select
          { ...rest }
          ref={ (c) => { this.select = c; } }
          className={ classes }
          name={ name }
          id={ id }
          required={ required }
          onFocus={ this.handleFocus }
          onBlur={ this.handleBlur }
          onChange={ this.handleChange }
          value={ value }
          multiple={ multiple }
        >
          { children }
        </select>
        { !multiple && <Icon name="chevron" className={ css.arrow } /> }
        <CSSTransitionGroup
          className={ css.post }
          transitionName={ css }
          transitionEnterTimeout={ 500 }
          transitionLeaveTimeout={ 300 }
          transitionAppearTimeout={ 500 }
          transitionAppear
        >
          { error && error.length > 0 && (
            <div
              className={ css.errorMsg }
            >
              { error }
            </div>
          ) }
        </CSSTransitionGroup>
      </div>
    );
  }
}<commit_msg>Unify `<Select />` className/classNames prop API with `<Input />`<commit_after>import React, { Component, PropTypes } from 'react';
import CSSTransitionGroup from 'react-addons-css-transition-group';
import cx from 'classnames';

import mergeObjectStrings from '../../../utils/mergeObjectStrings/mergeObjectStrings';
import Icon from '../../Icon/Icon';
import noop from '../../../utils/noop';
import css from './Select.css';

export default class Select extends Component {
  static propTypes = {
    onFocus: PropTypes.func,
    onBlur: PropTypes.func,
    onChange: PropTypes.func,
    name: PropTypes.string,
    id: PropTypes.string,
    required: PropTypes.bool,
    classNames: PropTypes.shape({
      wrapper: PropTypes.string,
      select: PropTypes.string,
      high: PropTypes.string,
      error: PropTypes.string,
      post: PropTypes.string,
      errorMsg: PropTypes.string,
      enter: PropTypes.string,
      enterActive: PropTypes.string,
      appear: PropTypes.string,
      appearActive: PropTypes.string,
      leave: PropTypes.string,
      leaveActive: PropTypes.string,
    }),
    hasError: PropTypes.bool,
    multiple: PropTypes.bool,
    children: PropTypes.node.isRequired,
    value: PropTypes.oneOfType([
      PropTypes.string,
      PropTypes.array,
    ]),
    error: PropTypes.string,
    priority: PropTypes.oneOf(['high']),
  };

  static defaultProps = {
    onChange: noop,
    onFocus: noop,
    onBlur: noop,
  };

  state = {
    hasFocus: false,
  }

  focus = () => {
    this.select.focus();
    this.handleFocus();
  }

  blur = () => {
    this.select.blur();
    this.handleBlur();
  }

  handleFocus = () => {
    const { onFocus } = this.props;
    this.setState({ hasFocus: true }, onFocus);
  }

  handleBlur = () => {
    const { onBlur } = this.props;
    this.setState({ hasFocus: false }, onBlur);
  }

  handleChange = (e) => {
    const { onChange, name, multiple } = this.props;
    const value = multiple
      ? [].filter.call(this.select.options, o => o.selected).map(o => o.value)
      : e.target.value;

    onChange(e, name, value);
  }

  render() {
    const { hasFocus } = this.state;

    const {
      name,
      id,
      required,
      error,
      classNames,
      multiple,
      value,
      children,
      priority,
      ...rest,
    } = this.props;

    const mergedClassNames = mergeObjectStrings(css, classNames);

    const classes = cx(
      mergedClassNames.select,
      hasFocus ? mergedClassNames.focus : null,
      error ? css.error : null,
      css[priority],
    );

    return (
      <div className={ mergedClassNames.wrapper }>
        <select
          { ...rest }
          ref={ (c) => { this.select = c; } }
          className={ classes }
          name={ name }
          id={ id }
          required={ required }
          onFocus={ this.handleFocus }
          onBlur={ this.handleBlur }
          onChange={ this.handleChange }
          value={ value }
          multiple={ multiple }
        >
          { children }
        </select>
        { !multiple && <Icon name="chevron" className={ mergedClassNames.arrow } /> }
        <CSSTransitionGroup
          className={ mergedClassNames.post }
          transitionName={ css }
          transitionEnterTimeout={ 500 }
          transitionLeaveTimeout={ 300 }
          transitionAppearTimeout={ 500 }
          transitionAppear
        >
          { error && error.length > 0 && (
            <div
              className={ mergedClassNames.errorMsg }
            >
              { error }
            </div>
          ) }
        </CSSTransitionGroup>
      </div>
    );
  }
}
{'fraction_non_alphanumeric': 0.13382730984424618, 'fraction_numerical': 0.0030243459851807047, 'mean_word_length': 1.999546485260771, 'pattern_counts': {'":': 0, '<': 23, '<?xml version=': 0, '>': 41, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '6696844', 'n_tokens_mistral': 1962, 'n_tokens_neox': 1966, 'n_words': 434}