在React

时间:2015-10-03 03:37:36

标签: reactjs reactjs-flux flux

我一直在为我的React应用程序应用类似Flux的架构,并且想知道应用程序状态是否真的要存储在商店而不是组件中。似乎有些情况下某些组件可能保持自己的状态。

例如,下面是自我意识FormElement。我无法想象使用类似Flux的架构来编写它,其中所有内容都作为动作发送到商店。商店如何跟踪所有不同的表单元素及其父表单?

简而言之:让某些组件跟踪自己的状态是否可以接受,而大多数其他组件使用dispatch?

FormElement = React.createClass({
  displayName: 'FormElement',

  validations: {
    email: /^[A-Za-z0-9-._+]+@[A-Za-z0-9-]+[.A-Za-z0-9-]*\.[A-Za-z]{2,}$/,
    password: /.{6,}/
  },

  propTypes: {
    id: React.PropTypes.string.isRequired,
    label: React.PropTypes.string.isRequired,
    type: React.PropTypes.string,
    required: React.PropTypes.bool
  },

  getDefaultProps() {
    return {
      type: 'text',
      required: false,
      disabled: false
    }
  },

  getInitialState() {
    return {
      focused: false,
      filled: false,
      valid: true,
      invalidMessage: ''
    }
  },

  handleFocus(focusing) {
    let valid = true, errMsg = '';
    let inputVal = React.findDOMNode(this.refs.inputField).value;

    this.setState({focused: focusing});

    if (!focusing) {
      // Do some validations on blur
      if (this.props.required && !this.state.filled) {
        valid = false;
        errMsg = this.props.label + ' is required';
      }

      if (this.props.type === 'email' &&
        this.state.filled && !this.validFormat(inputVal, 'email')) {
        valid = false;
        errMsg = 'Invalid email address';
      } else if (this.props.type === 'password' &&
        this.state.filled && !this.validFormat(inputVal, 'password')) {
        valid = false;
        errMsg = 'Password too short';
      }
    }

    this.setState({valid, invalidMessage: errMsg}, function () {
      // Notify parent that something changed
      //this.props.onAction(this);
    });
  },

  handleChange({target}) {
    this.setState({
      value: target.value,
      filled: target.value.length > 0
    });
  },

  validFormat(str, type) {
    return !!str.match(this.validations[type]);
  },

  render() {
    let formElement;
    const labelClasses = classNames({
      'focused': this.state.focused || this.state.filled
    });
    const groupClasses = classNames({
      'form-group': true,
      'has-error': !this.state.valid
    });

    if (_.contains(['text', 'email', 'password'], this.props.type)) {
      formElement = (
        <div className={groupClasses}>
          <label
            className={labelClasses}
            htmlFor={this.props.id}>
            {this.state.invalidMessage ?
              this.state.invalidMessage : this.props.label}
          </label>

          <input type={this.props.type}
                 className="form-control"
                 id={this.props.id}
                 ref="inputField"
                 onFocus={this.handleFocus.bind(null, true)}
                 onBlur={this.handleFocus.bind(null, false)}
                 onChange={this.handleChange}
                 disabled={this.props.disabled} />
        </div>
      );
    } else if (this.props.type === 'submit') {
      formElement = (
        <div>
          <button type="submit"
                  className="btn btn-primary"
                  disabled={this.props.disabled}>{this.props.label}
          </button>
        </div>
      );
    }

    return formElement;
  }
});

1 个答案:

答案 0 :(得分:0)

磁通模式主要用于处理服务器和组件之间的数据。我还使用app.store来处理影响多个组件的状态,并使用api.store来处理处理服务器api(请求或保存数据)的操作。

如果状态的范围仅涉及单个组件,则可以包含组件中的状态。