I want to write a short post about how I solved the inheritance problem in ReactJS. Usually, on forums, people advise using mixins to inherit functionality, but, in my opinion, this is not entirely correct. Still, traits / mixins and classes are not the same thing, and because of the possibility of multiple inheritance, such incidents can occur:
var A = { doStuff (){} } var B = { doStuff (){} } var C = React.createClass({ mixins: [A, B] });
In addition, mixins do not allow standard OOPshnye chips to do like rewriting methods (method override):
')
var A = { doStuff (){} } var C = React.createClass({ mixins: [A], doStuff (){
And without this, of course, the functionality expansion as in the “adult” OOP languages ​​will not work either:
doStuff (){ super.doStuff()
Of course, the ES6 classes will solve this problem, and the ReactJS team is preparing for this, judging by the posts on their blog, but wait for ES6 as a second coming, and then, you will have to wait until the old Internet Explorer has died without ES6 support.
So, I want to offer you an alternative method that I use myself, but for this you will need:
1) The system of modules / dependencies: RequireJS / Browserify / WebPack / that is still there in fashion. If you don’t use / don’t know what JavaScript modules are, well, it's time to
find out .
2) Any function / lib for deep copying of objects, for example, jQuery.extend, _.extend, etc.
So, I write modules of my components as follows:
var React = require('react'); var Human = { whoAreYou (){ return "I'm a human"; } whatDoYouDo (){ return "I'm just chilling"; } render (){ return ( <h1>{this.whoAreYou()}<small>{this.whatDoYouDo()}</small></h1> ) } } module.exports = { Class: Human, Component: React.createClass(Human) }
The trick is that I export not only the component, but also the “clean” object from which this component is created, so when I have to use just the <Human /> component, I take the Component field from the export of my module:
var Human = require('human').Component;
But when I need to inherit from my module, and here the most interesting begins, I use the Class field:
var React = require('react'); var Parent = require('human').Class; var Programmer = {}; jQuery.extend(true, Programmer, Parent, { whoAreYou (){ return Parent.whoAreYou.apply(this) + " and a programmer";
Naturally, I also export this module according to the above-described “convention”:
module.exports = { Class: Programmer, Component: React.createClass(Programmer) }
And now it can be used in the application:
var Programmer = require('programmer').Component;
Well, or inherit / extend further, for example, in JuniorDeveloper.
And that's all, it was my short post about a crutch for (pseudo) inheritance in ReactJS. Have a successful work week, gentlemen!