<commit_before>import BaseComponent from 'base-component'
import classNames from 'classnames'
import defined from '@xen-orchestra/defined'
import Icon from 'icon'
import map from 'lodash/map'
import PropTypes from 'prop-types'
import randomPassword from 'random-password'
import React from 'react'
import round from 'lodash/round'
import SingleLineRow from 'single-line-row'
import { Container, Col } from 'grid'
import { DropdownButton, MenuItem } from 'react-bootstrap-4/lib'

import Button from '../button'
import Component from '../base-component'
import getEventValue from '../get-event-value'
import { formatSizeRaw, parseSize } from '../utils'

export Number from './number'
export Select from './select'

// ===================================================================

export class Password extends Component {
  static propTypes = {
    enableGenerator: PropTypes.bool,
  }

  get value () {
    return this.refs.field.value
  }

  set value (value) {
    this.refs.field.value = value
  }

  _generate = () => {
    const value = randomPassword(8)
    const isControlled = this.props.value !== undefined
    if (isControlled) {
      this.props.onChange(value)
    } else {
      this.refs.field.value = value
    }

    // FIXME: in controlled mode, visibility should only be updated
    // when the value prop is changed according to the emitted value.
    this.setState({
      visible: true,
    })
  }

  _toggleVisibility = () => {
    this.setState({
      visible: !this.state.visible,
    })
  }

  render () {
    const { className, enableGenerator = false, ...props } = this.props
    const { visible } = this.state

    return (
      <div className='input-group'>
        {enableGenerator && (
          <span className='input-group-btn'>
            <Button onClick={this._generate}>
              <Icon icon='password' />
            </Button>
          </span>
        )}
        <input
          {...props}
          className={classNames(className, 'form-control')}
          ref='field'
          type={visible ? 'text' : 'password'}
        />
        <span className='input-group-btn'>
          <Button onClick={this._toggleVisibility}>
            <Icon icon={visible ? 'shown' : 'hidden'} />
          </Button>
        </span>
      </div>
    )
  }
}

// ===================================================================

export class Range extends Component {
  static propTypes = {
    max: PropTypes.number.isRequired,
    min: PropTypes.number.isRequired,
    onChange: PropTypes.func,
    required: PropTypes.boolean,
    step: PropTypes.number,
    value: PropTypes.number,
  }

  componentDidMount () {
    const { min, onChange, required, value } = this.props

    if (value === undefined && required) {
      onChange !== undefined && onChange(min)
    }
  }

  _onChange = value => this.props.onChange(getEventValue(value))

  render () {
    const { max, min, step, value } = this.props<commit_msg>fix(xo-web/form/range): fix required prop type<commit_after>import BaseComponent from 'base-component'
import classNames from 'classnames'
import defined from '@xen-orchestra/defined'
import Icon from 'icon'
import map from 'lodash/map'
import PropTypes from 'prop-types'
import randomPassword from '<PASSWORD>'
import React from 'react'
import round from 'lodash/round'
import SingleLineRow from 'single-line-row'
import { Container, Col } from 'grid'
import { DropdownButton, MenuItem } from 'react-bootstrap-4/lib'

import Button from '../button'
import Component from '../base-component'
import getEventValue from '../get-event-value'
import { formatSizeRaw, parseSize } from '../utils'

export Number from './number'
export Select from './select'

// ===================================================================

export class Password extends Component {
  static propTypes = {
    enableGenerator: PropTypes.bool,
  }

  get value () {
    return this.refs.field.value
  }

  set value (value) {
    this.refs.field.value = value
  }

  _generate = () => {
    const value = randomPassword(8)
    const isControlled = this.props.value !== undefined
    if (isControlled) {
      this.props.onChange(value)
    } else {
      this.refs.field.value = value
    }

    // FIXME: in controlled mode, visibility should only be updated
    // when the value prop is changed according to the emitted value.
    this.setState({
      visible: true,
    })
  }

  _toggleVisibility = () => {
    this.setState({
      visible: !this.state.visible,
    })
  }

  render () {
    const { className, enableGenerator = false, ...props } = this.props
    const { visible } = this.state

    return (
      <div className='input-group'>
        {enableGenerator && (
          <span className='input-group-btn'>
            <Button onClick={this._generate}>
              <Icon icon='password' />
            </Button>
          </span>
        )}
        <input
          {...props}
          className={classNames(className, 'form-control')}
          ref='field'
          type={visible ? 'text' : 'password'}
        />
        <span className='input-group-btn'>
          <Button onClick={this._toggleVisibility}>
            <Icon icon={visible ? 'shown' : 'hidden'} />
          </Button>
        </span>
      </div>
    )
  }
}

// ===================================================================

export class Range extends Component {
  static propTypes = {
    max: PropTypes.number.isRequired,
    min: PropTypes.number.isRequired,
    onChange: PropTypes.func,
    required: PropTypes.bool,
    step: PropTypes.number,
    value: PropTypes.number,
  }

  componentDidMount () {
    const { min, onChange, required, value } = this.props

    if (value === undefined && required) {
      onChange !== undefined && onChange(min)
    }
  }

  _onChange = value => this.props.onChange(getEventValue(value))

  render () {
    const { max, min, step, value } = this.props
{'fraction_non_alphanumeric': 0.16697556866048863, 'fraction_numerical': 0.0006739679865206403, 'mean_word_length': 2.7688888888888887, 'pattern_counts': {'":': 0, '<': 30, '<?xml version=': 0, '>': 36, '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': '3092910', 'n_tokens_mistral': 1658, 'n_tokens_neox': 1633, 'n_words': 439}