Facebook React에서 코드 재사용을 위해 mixins vs components 사용
저는 Backbone 프로젝트에서 Facebook React를 사용하기 시작했고, 지금까지는 잘 되어가고 있습니다.
하지만 리액트 코드에 중복이 섞여 있는 것을 알 수 있었습니다.
예를 들어 다음과 같은 상태를 가진 여러 양식 위젯이 있습니다.INITIAL
,SENDING
★★★★★★★★★★★★★★★★★」SENT
유효성이 상태가 갱신됩니다 버튼을 누르면 폼의 유효성을 확인하고 요청을 한 후 상태를 갱신해야 합니다.는 리액트 에 유지됩니다.this.state
★★★★★★★★★★★★★★★★★★★★★★★★★★★
뷰라면, 「Backbone」, 「Base Class」라고 하는 입니다.FormView
하지만 내 인상은 React가 뷰 로직을 공유하는 하위 분류를 지지하지도 않는다는 것이었다(내가 틀렸다면 정정해 달라).
React에서 코드 재사용을 위한 두 가지 접근 방식을 보았습니다.
- Mixins (React에 부속된 Linked State Mixin 등)
- 컨테이너 컴포넌트(react-infinite-scroll 등).
React에서 상속하는 것보다 믹스인과 컨테이너를 선호하는 것이 맞습니까?이것은 고의적인 설계 결정입니까?두 번째 단락의 "양식 위젯" 예제에 혼합 또는 용기 구성요소를 사용하는 것이 더 의미가 있습니까?
여기 그들의 현재 상태에 대한 요지가 있다.그들은 비슷한 구조를 가지고 있다.beginSend
둘 다 검증 지원이 필요합니다(아직은 필요 없음).
데이: 이이답답답답래래래래오다다다다다.가능하면 믹스인에 접근하지 마세요.★★★★★★★★★★★★★★★★!
믹스인은 죽었다. 작곡
에는 이 하여 이 서브 컴포넌트를 추출하려고 .FormWidget
★★★★★★★★★★★★★★★★★」InputWidget
단, 생성된 것을 보다 잘 제어하고 싶었기 때문에 이 접근방식을 중도에 포기했습니다.input
아, 아, 아, 아, 아, 아, 아, 아, 아.
가장 큰 도움이 된 기사 두 개:
- React에서 생각하면서 실제로 이 작업에 중첩된 컴포넌트를 원하지 않는다는 것을 깨달았습니다.
- 재사용 가능한 컴포넌트에는 깔끔한 믹스인 예가 있습니다.
두 믹스인만 .ValidationMixin
★★★★★★★★★★★★★★★★★」FormMixin
.
가가구구 구구구구
검증 믹신
중 'd" 저장하는 합니다.state.errors
배열을 지정하여 해당 필드를 강조 표시할 수 있습니다.
소스(gist)
define(function () {
'use strict';
var _ = require('underscore');
var ValidationMixin = {
getInitialState: function () {
return {
errors: []
};
},
componentWillMount: function () {
this.assertValidatorsDefined();
},
assertValidatorsDefined: function () {
if (!this.validators) {
throw new Error('ValidatorMixin requires this.validators to be defined on the component.');
}
_.each(_.keys(this.validators), function (key) {
var validator = this.validators[key];
if (!_.has(this.state, key)) {
throw new Error('Key "' + key + '" is defined in this.validators but not present in initial state.');
}
if (!_.isFunction(validator)) {
throw new Error('Validator for key "' + key + '" is not a function.');
}
}, this);
},
hasError: function (key) {
return _.contains(this.state.errors, key);
},
resetError: function (key) {
this.setState({
'errors': _.without(this.state.errors, key)
});
},
validate: function () {
var errors = _.filter(_.keys(this.validators), function (key) {
var validator = this.validators[key],
value = this.state[key];
return !validator(value);
}, this);
this.setState({
'errors': errors
});
return _.isEmpty(errors);
}
};
return ValidationMixin;
});
사용.
ValidationMixin
에는 다음 3가지 방법이 있습니다.validate
,hasError
그리고.resetError
.
클래스가 정의되기를 기대합니다.validators
오브젝트, 유사propTypes
:
var JoinWidget = React.createClass({
mixins: [React.addons.LinkedStateMixin, ValidationMixin, FormMixin],
validators: {
email: Misc.isValidEmail,
name: function (name) {
return name.length > 0;
}
},
// ...
});
유저가 송신 버튼을 누르면, 나는 전화한다.validate
에의 문의validate
각 검증자를 실행하고 를 채웁니다.this.state.errors
검증에 실패한 속성의 키가 포함된 어레이를 사용합니다.
인마이render
사용방법hasError
필드의 올바른 CSS 클래스를 생성합니다.사용자가 필드에 포커스를 놓으면resetError
다음까지 오류 강조 표시를 삭제하다validate
불러.
renderInput: function (key, options) {
var classSet = {
'Form-control': true,
'Form-control--error': this.hasError(key)
};
return (
<input key={key}
type={options.type}
placeholder={options.placeholder}
className={React.addons.classSet(classSet)}
valueLink={this.linkState(key)}
onFocus={_.partial(this.resetError, key)} />
);
}
폼믹신
폼 믹스인은 폼 상태(편집 가능, 송신, 송신)를 처리합니다.요청을 보내는 동안 입력 및 버튼을 비활성화하고 요청을 보낼 때 그에 따라 보기를 업데이트할 수 있습니다.
소스(gist)
define(function () {
'use strict';
var _ = require('underscore');
var EDITABLE_STATE = 'editable',
SUBMITTING_STATE = 'submitting',
SUBMITTED_STATE = 'submitted';
var FormMixin = {
getInitialState: function () {
return {
formState: EDITABLE_STATE
};
},
componentDidMount: function () {
if (!_.isFunction(this.sendRequest)) {
throw new Error('To use FormMixin, you must implement sendRequest.');
}
},
getFormState: function () {
return this.state.formState;
},
setFormState: function (formState) {
this.setState({
formState: formState
});
},
getFormError: function () {
return this.state.formError;
},
setFormError: function (formError) {
this.setState({
formError: formError
});
},
isFormEditable: function () {
return this.getFormState() === EDITABLE_STATE;
},
isFormSubmitting: function () {
return this.getFormState() === SUBMITTING_STATE;
},
isFormSubmitted: function () {
return this.getFormState() === SUBMITTED_STATE;
},
submitForm: function () {
if (!this.isFormEditable()) {
throw new Error('Form can only be submitted when in editable state.');
}
this.setFormState(SUBMITTING_STATE);
this.setFormError(undefined);
this.sendRequest()
.bind(this)
.then(function () {
this.setFormState(SUBMITTED_STATE);
})
.catch(function (err) {
this.setFormState(EDITABLE_STATE);
this.setFormError(err);
})
.done();
}
};
return FormMixin;
});
사용.
컴포넌트가 다음 한 가지 방법을 제공할 것으로 예상합니다.sendRequest
블루버드 약속을 돌려줘야지(Q 또는 다른 약속 라이브러리와 연동하도록 수정하는 것은 간단합니다).
다음과 같은 편리한 방법을 제공합니다.isFormEditable
,isFormSubmitting
그리고.isFormSubmitted
또, 요구를 개시하는 방법도 있습니다.submitForm
수 있습니다.onClick
핸들러
React로 SPA를 만들고 있는데(1년 전부터 생산) 믹스인은 거의 사용하지 않습니다.
에 대한 React의 방식React)을 을 공유하는 입니다.componentDidMount
이 문제는 Dan Abramov가 링크에서 말하는 고차 컴포넌트(또는 ES6 클래스 상속 사용)로 해결됩니다.
또한 혼합은 React의 숨겨진 컨텍스트 기능을 사용하여 프레임워크 API를 모든 구성요소에서 사용할 수 있도록 하기 위해 프레임워크에서 자주 사용됩니다.이는 ES6 클래스 상속에서도 더 이상 필요하지 않습니다.
대부분의 경우 믹스인이 사용되지만 실제로는 필요하지 않으며 간단한 도우미로 대체될 수 있습니다.
예를 들어 다음과 같습니다.
var WithLink = React.createClass({
mixins: [React.addons.LinkedStateMixin],
getInitialState: function() {
return {message: 'Hello!'};
},
render: function() {
return <input type="text" valueLink={this.linkState('message')} />;
}
});
리팩터링 할 수 요.LinkedStateMixin
을 사용하다
var WithLink = React.createClass({
getInitialState: function() {
return {message: 'Hello!'};
},
render: function() {
return <input type="text" valueLink={LinkState(this,'message')} />;
}
});
큰 차이가 있나요?
언급URL : https://stackoverflow.com/questions/21854938/using-mixins-vs-components-for-code-reuse-in-facebook-react
'programing' 카테고리의 다른 글
JSONARray에서 특정 요소를 제거하려면 어떻게 해야 합니까? (0) | 2023.03.28 |
---|---|
WordPress 웹사이트에서 프런트 엔드에서 wp-admin/ajax.php 페이지에 액세스하면 403 오류가 나타난다. (0) | 2023.03.28 |
3진 연산자의 각도 변환 필터 (0) | 2023.03.28 |
Postgre의 JSON 데이터 유형 크기 제한SQL (0) | 2023.03.28 |
URL 없이 상태 간에 데이터를 전달하는 AngularJS UI 라우터 (0) | 2023.03.28 |