Je commence à utiliser Facebook React dans un projet Backbone et jusqu'à présent ça se passe très bien.
Cependant, j'ai remarqué une duplication s'insinuant dans mon code React.
Par exemple, j'ai plusieurs widgets de type formulaire avec des états comme INITIAL
, SENDING
et SENT
. Lorsqu'un bouton est enfoncé, le formulaire doit être validé, une demande est effectuée, puis l'état est mis à jour. L'état est this.state
bien sûr conservé dans React , avec les valeurs de champ.
Si c'étaient des vues Backbone, j'aurais extrait une classe de base appelée FormView
mais mon impression était que React n'approuve ni ne prend en charge le sous-classement pour partager la logique de vue (corrigez-moi si je me trompe).
J'ai vu deux approches de la réutilisation du code dans React:
- Mixins (comme LinkedStateMixin fourni avec React);
- Composants de conteneur (tels que react-infinite-scroll ).
Ai-je raison de dire que les mixins et les conteneurs sont préférés à l'héritage dans React? Est-ce une décision délibérée de conception? Serait-il plus logique d'utiliser un mixin ou un composant conteneur pour mon exemple de «widget de formulaire» du deuxième paragraphe?
Voici un aperçu de FeedbackWidget
et JoinWidget
dans leur état actuel . Ils ont une structure similaire, une beginSend
méthode similaire et devront tous deux avoir un support de validation (pas encore là).
la source
Réponses:
Au début, j'ai essayé d'utiliser des sous-composants pour cela et d'extraire
FormWidget
etInputWidget
. Cependant, j'ai abandonné cette approche à mi-chemin car je voulais un meilleur contrôle sur les générésinput
et leur état.Deux articles qui m'ont le plus aidé:
Il s'est avéré que je n'avais besoin que d'écrire deux mixins (différents):
ValidationMixin
etFormMixin
.Voici comment je les ai séparés.
ValidationMixin
Validation mixin ajoute des méthodes pratiques pour exécuter vos fonctions de validation sur certaines des propriétés de votre état et stocker les propriétés «d'erreur» dans un
state.errors
tableau afin que vous puissiez mettre en évidence les champs correspondants.Source ( essentiel )
Usage
ValidationMixin
a trois méthodes:validate
,hasError
etresetError
.Il s'attend à ce que la classe définisse l'
validators
objet, similaire àpropTypes
:Lorsque l'utilisateur appuie sur le bouton de soumission, j'appelle
validate
. Un appel àvalidate
exécutera chaque validateur et remplirathis.state.errors
avec un tableau contenant les clés des propriétés dont la validation a échoué.Dans ma
render
méthode, j'utilisehasError
pour générer une classe CSS correcte pour les champs. Lorsque l'utilisateur met le focus dans le champ, j'appelleresetError
pour supprimer la surbrillance d'erreur jusqu'au prochainvalidate
appel.FormMixin
Form mixin gère l'état du formulaire (modifiable, soumis, soumis). Vous pouvez l'utiliser pour désactiver les entrées et les boutons pendant l'envoi de la demande, et pour mettre à jour votre vue en conséquence lorsqu'elle est envoyée.
Source ( essentiel )
Usage
Il s'attend à ce que le composant fournisse une méthode:,
sendRequest
qui devrait renvoyer une promesse Bluebird. (Il est simple de le modifier pour qu'il fonctionne avec Q ou une autre bibliothèque de promesses.)Il fournit des méthodes pratiques telles que
isFormEditable
,isFormSubmitting
etisFormSubmitted
. Il fournit également une méthode pour lancer la demande:submitForm
. Vous pouvez l'appeler à partir duonClick
gestionnaire des boutons de formulaire .la source
FormInput
qui parle à son propriétaire viaformLink
.formLink
est similaire àvalueLink
, et est renvoyé parFormMixin
lalinkValidatedState(name, validator)
méthode de.FormInput
tire sa valeur deformLink.value
et appelleformLink.requestBlur
etformLink.requestFocus
- ils provoquent la validation dansFormMixin
. Enfin, pour personnaliser le composant utilisé pour l'entrée, je peux le transmettre àFormInput
:<FormInput component={React.DOM.textarea} ... />
done
bluebird et le code fonctionnera tel quel dans Q (ou promesses natives) - bien sûr, bluebird est meilleur. Notez également que la syntaxe a changé dans React depuis la réponse.Je construis un SPA avec React (en production depuis 1 an), et je n'utilise presque jamais de mixins.
Le seul cas d'utilisation que j'ai actuellement pour les mixins est lorsque vous souhaitez partager un comportement qui utilise les méthodes de cycle de vie de React (
componentDidMount
etc.). Ce problème est résolu par les composants d'ordre supérieur que Dan Abramov parle dans son lien (ou en utilisant l'héritage de classe ES6).Les mixins sont également souvent utilisés dans les frameworks, pour rendre l'API du framework disponible à tous les composants, en utilisant la fonctionnalité de contexte "caché" de React. Cela ne sera plus nécessaire non plus avec l'héritage de classe ES6.
La plupart du temps, les mixins sont utilisés, mais ne sont pas vraiment nécessaires et pourraient être facilement remplacés par de simples helpers.
Par exemple:
Vous pouvez très facilement refactoriser le
LinkedStateMixin
code afin que la syntaxe soit:Y a-t-il une grande différence?
la source