Skip to content

Commit

Permalink
fix(react-core): fixes crash when using with webpack-dev-server and H…
Browse files Browse the repository at this point in the history
…ot Module Reloading (#694)
  • Loading branch information
tpisto authored and MaximKudriavtsev committed Jan 26, 2018
1 parent 8502904 commit bdc944b
Show file tree
Hide file tree
Showing 5 changed files with 31 additions and 37 deletions.
3 changes: 3 additions & 0 deletions packages/dx-react-core/src/plugged/action.jsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import React from 'react';
import PropTypes from 'prop-types';
import { INDEXABLE_COMPONENT } from './plugin-indexer';

export class Action extends React.PureComponent {
componentWillMount() {
Expand All @@ -26,6 +27,8 @@ export class Action extends React.PureComponent {
}
}

Action[INDEXABLE_COMPONENT] = true;

Action.propTypes = {
position: PropTypes.func,
name: PropTypes.string.isRequired,
Expand Down
3 changes: 3 additions & 0 deletions packages/dx-react-core/src/plugged/getter.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import {
getAvailableGetters,
getAvailableActions,
} from '../utils/plugin-helpers';
import { INDEXABLE_COMPONENT } from './plugin-indexer';

export const UPDATE_CONNECTION = 'updateConnection';

Expand Down Expand Up @@ -59,6 +60,8 @@ export class Getter extends React.PureComponent {
}
}

Getter[INDEXABLE_COMPONENT] = true;

Getter.propTypes = {
position: PropTypes.func,
name: PropTypes.string.isRequired,
Expand Down
9 changes: 3 additions & 6 deletions packages/dx-react-core/src/plugged/plugin-indexer.jsx
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Getter } from './getter';
import { Action } from './action';
import { Template } from './template';

export const INDEXABLE_COMPONENT = Symbol('indexableComponent');

export const PluginIndexer = (
{ children },
Expand All @@ -19,9 +18,7 @@ export const PluginIndexer = (
return [...calculatedPosition, index];
};

if (child.type === Getter ||
child.type === Action ||
child.type === Template) {
if (child.type[INDEXABLE_COMPONENT] === true) {
return React.cloneElement(child, { position: childPosition });
}

Expand Down
49 changes: 19 additions & 30 deletions packages/dx-react-core/src/plugged/plugin-indexer.test.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,20 +3,10 @@ import PropTypes from 'prop-types';
import { mount } from 'enzyme';
import { setupConsole } from '@devexpress/dx-testing';

import { PluginIndexer } from './plugin-indexer';
import { Getter } from './getter';
import { Template } from './template';
import { Action } from './action';
import { PluginIndexer, INDEXABLE_COMPONENT } from './plugin-indexer';

jest.mock('./getter', () => ({
Getter: () => null,
}));
jest.mock('./action', () => ({
Action: () => null,
}));
jest.mock('./template', () => ({
Template: () => null,
}));
const Test = () => null;
Test[INDEXABLE_COMPONENT] = true;

describe('PluginIndexer', () => {
let resetConsole;
Expand All @@ -30,51 +20,50 @@ describe('PluginIndexer', () => {
it('should correctly determine plugin position', () => {
const tree = mount((
<PluginIndexer>
<Getter />
<Action />
<Template />
<Test />
</PluginIndexer>
));

expect([tree.find(Getter), tree.find(Action), tree.find(Template)]
expect(tree.find(Test)
.map(wrapper => wrapper.prop('position')()))
.toEqual([[0], [1], [2]]);
.toEqual([[0]]);
});

it('should correctly determine plugin position after children change', () => {
const Test = ({ enableGetter }) => (
const Test1 = ({ enableGetter }) => (
<PluginIndexer>
{enableGetter && <Getter />}
<Action />
<Template />
{enableGetter && <Test />}
<Test />
</PluginIndexer>
);
Test.propTypes = {
Test1.propTypes = {
enableGetter: PropTypes.bool.isRequired,
};

const tree = mount(<Test enableGetter={false} />);
const tree = mount(<Test1 enableGetter={false} />);

tree.setProps({ enableGetter: true });
expect([tree.find(Getter), tree.find(Action), tree.find(Template)]
const tests = tree.find(Test);
expect([tests.at(0), tests.at(1)]
.map(wrapper => wrapper.prop('position')()))
.toEqual([[0], [1], [2]]);
.toEqual([[0], [1]]);
});

it('should correctly determine plugin position within another component', () => {
const tree = mount((
<PluginIndexer>
<div>
<PluginIndexer>
<Getter />
<Action />
<Test />
<Test />
</PluginIndexer>
</div>
<Template />
<Test />
</PluginIndexer>
));

expect([tree.find(Getter), tree.find(Action), tree.find(Template)]
const tests = tree.find(Test);
expect([tests.at(0), tests.at(1), tests.at(2)]
.map(wrapper => wrapper.prop('position')()))
.toEqual([[0, 0], [0, 1], [1]]);
});
Expand Down
4 changes: 3 additions & 1 deletion packages/dx-react-core/src/plugged/template.jsx
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import React from 'react';
import PropTypes from 'prop-types';
import { INDEXABLE_COMPONENT } from './plugin-indexer';

export const RERENDER_TEMPLATE = 'rerenderTemplate';

let globalTemplateId = 0;
export class Template extends React.PureComponent {
constructor(props, context) {
Expand Down Expand Up @@ -38,6 +38,8 @@ export class Template extends React.PureComponent {
}
}

Template[INDEXABLE_COMPONENT] = true;

Template.propTypes = {
position: PropTypes.func,
name: PropTypes.string.isRequired,
Expand Down

0 comments on commit bdc944b

Please sign in to comment.