2016-08-03 4 views
2

Я работаю над примерами ответов, и я забирал некоторые компоненты. Теперь я чувствую, что сталкиваюсь с фундаментальным «Brain Fart», касающимся структуры компонентов и гнездования.Передача JSX компонентам vs dangerouslySetInnerHTML

Что я после:

Входной компонент с факультативным этикетки и текст справки.

То, что я прямо сейчас: (который делает работу)

Input.js

//...// 
var MyInput = React.createClass({ 

render: function() { 

    //...// 

    var helpText = null; 

    if(typeof this.props.helpText !== 'undefined'){ 
     helpText = <p className="help-block" > {this.props.helpText} </p>; 
    } 

    return (
     <div className={ className }> 
     <MyLabel showLabel={ this.props.showLabel} htmlFor={ this.props.name }> 
      { this.props.title } 
     </MyLabel> 
     <input 
      type={ this.props.type || 'text' } 
      name={ this.props.name } 
      onChange={ this.changeValue } 
      value={ this.getValue() } 
      checked={ this.props.type === 'checkbox' && this.getValue() ? 'checked' : null } 
      placeholder={ this.props.title } 
     /> 
      <span className='validation-error'>{ errorMessage }</span> 
      {helpText} 
     </div> 
    ); 
    } 
}); 

module.exports = MyInput; 

LoginForm.js

//...// 

var LoginForm = React.createClass({ 

    // ... // 

    render: function() { 
     return (
      <Form className=" col-sm-11 col-lg-10 block-center loginFrm" > 

       <div className="row"> 
        <FrmInput value ="" 
          name="username" 
          title="Username" 
          className="col-sm-5" 
          showLabel={false} 
          helpText= { <span> Help text with <a href="#"> link </a> </span>} 
          required /> 
        <FrmInput value ="" 
          type="password" 
          name="password" 
          title="Password" 
          className="col-sm-5" 
          showLabel={false} 
          required /> 

        <button type="submit" 
         className="btn btn-default input-sm " 
         > 
         Sign In 
        </button> 

       </div> 

       <div className="row"> 
        <div className="pull-right" > 
         <FrmCheckbox name="rememberMe" 
          title="Remember Me" 
         /> 
        </div> 
       </div> 

      </Form> 
     ); 
    }, 

}); 

module.exports = LoginForm; 

Изготовление этикетки по желанию легко. Я использую свойство BOOL showLabel на компоненте <MyInput/> и передаю его в компонент MyLabel. showLabel считается TRUE, поэтому метка отображается, если вы не установили showLabel в false, как показано выше (тогда <MyLabel/> просто возвращает NULL).

Сначала я попробовал аналогичный метод с компонентом <help/>, чтобы добавить дополнительный текст справки после ввода внутри <MyInput/>. Все работало, пока я не добавил ссылку внутри текста справки. Изучив, я нашел dangerouslySetInnerHTML как средство передачи HTML-контента в компонент. Во время тестирования я также обнаружил, что вышеприведенный код также работает, хотя я точно не продаю, почему и как «хороший» этот подход.

Короче говоря, я просто передаю объекты JSX в свой компонент для рендеринга. внутри <Form> (от LoginForm.js) на <FrmInput/> компонента есть свойство с именем helpText устанавливается следующим образом

helpText= { <span> Help text with <a href="#"> link </a> </span> } 

внутри <MyInput/> компонента Я тестирование/прослушивание для helpText собственности и установить его в переменной, когда найдено (Опять же обертывание JSX)

var helpText = null; 

if(typeof this.props.helpText !== 'undefined'){ 
    helpText = <p className="help-block" > {this.props.helpText} </p>; 
} 

Затем в метод визуализации у меня есть { helpText }

все во всем похоже, что я просто передаю объекты javascript (через JSX) до окончательного метода рендеринга. Я не видел, как это использовалось в учебниках или документации, поэтому я просто ищу профессиональное мнение.

Является ли вышеприведенная «хорошая» практика или как ее лучше обрабатывать.

+1

Как вы это делаете, это хороший способ. Избегайте 'dangerouslySetInnerHTML' (как следует из названия), поскольку он может открыть вас до html инъекций, если вы не будете осторожны. Он также не позволит вам передавать контент, который имеет свою собственную обработку событий и т. Д. Используемый вами подход JSX означает, что кто-то передаст вам 'helpText', может фактически передать сложные компоненты с обработкой событий (события щелчка или что-то еще). – Brandon

ответ

2

Нет ничего плохого в вашем подходе. Несколько советов, которые могут помочь потоковой линии немного.

Вы можете сократить этот блок к простому инлайн тройным:

var helpText = null; 

if(typeof this.props.helpText !== 'undefined'){ 
    helpText = <p className="help-block" > {this.props.helpText} </p>; 
} 

Вы можете удалить выше и в рендеринге заменить {helpText} с:

{ this.props.helpText ? this.props.helpText : null } 

В формы ввода удалить встроенный HelpText HTML и перейдите к переменной, использующей parens для JSX.

const helpTextContent = (<span> Help text with <a href="#"> link </a> </span>); 

Затем инлайн: helpText = { helpTextContent }

Наконец, если вы используете ES6 вы можете использовать следующий синтаксис, чтобы сделать использование реквизита менее громоздким:

let { helpText, someOtherProp, anotherProp } = this.props;

Тогда вы можете просто обратиться к helpText или someOtherProp непосредственно без this.prop каждый раз.

Надеюсь, что это поможет!

+0

Спасибо за отзыв. – Nathan

Смежные вопросы