Skip to content
This repository has been archived by the owner on Aug 19, 2022. It is now read-only.

TypeError: Class constructors cannot be invoked without 'new' #443

Closed
GGAlanSmithee opened this issue Dec 5, 2015 · 7 comments
Closed

Comments

@GGAlanSmithee
Copy link

Hi.

I've been using Radium for a while and it's been working great!

However, since babel dropped support for decorators, I am experiencing an issue where I can't wrap a component (which is an ES6 class) with Radium.

Error

TypeError: Class constructors cannot be invoked without 'new'
   at RadiumEnhancer.Component (component.js:4:1)
   at new RadiumEnhancer (/home/ubuntu/workspace/node_modules/radium/lib/enhancer.js:85:26)
   at [object Object].ReactCompositeComponentMixin.mountComponent (/home/ubuntu/workspace/node_modules/react/lib/ReactCompositeComponent.js:148:18)
   at [object Object].wrapper [as mountComponent] (/home/ubuntu/workspace/node_modules/react/lib/ReactPerf.js:66:21)
   at Object.ReactReconciler.mountComponent (/home/ubuntu/workspace/node_modules/react/lib/ReactReconciler.js:37:35)
   at ReactDOMComponent.ReactMultiChild.Mixin.mountChildren (/home/ubuntu/workspace/node_modules/react/lib/ReactMultiChild.js:241:44)
   at ReactDOMComponent.Mixin._createContentMarkup (/home/ubuntu/workspace/node_modules/react/lib/ReactDOMComponent.js:591:32)
   at ReactDOMComponent.Mixin.mountComponent (/home/ubuntu/workspace/node_modules/react/lib/ReactDOMComponent.js:479:29)
   at Object.ReactReconciler.mountComponent (/home/ubuntu/workspace/node_modules/react/lib/ReactReconciler.js:37:35)
   at ReactDOMComponent.ReactMultiChild.Mixin.mountChildren (/home/ubuntu/workspace/node_modules/react/lib/ReactMultiChild.js:241:44)

This works

var Component = React.CreateClass({
    // ...
});

export default Radium(Component);

This does not

class Component extends React.Component {
    // ...
}

export default Radium(Component);

I do not know if using radium as a function (as opposed to using it as a decorator) works with an ES6 class, but your documentation suggests it should.

Thanks in advance!

@ianobermiller
Copy link
Contributor

Yes, it should, and there shouldn't be any difference between the function call and the decorator. I cannot reproduce this using JSBin, so I suspect there may be some other interaction with exports at play? Can you provide a repro in a github repro or bin?

@GGAlanSmithee
Copy link
Author

Sure!

Here it is.

$ node -v
v5.2.0

$ npm -v
3.5.3

(The lib versions are in the package.jsonfile)

to run:

$ npm i
$ babel --presets react index.js -o out.js
$ node out

result

TypeError: Class constructors cannot be invoked without 'new'
    at RadiumEnhancer.Component (/home/ubuntu/workspace/out.js:9:1)
    at new RadiumEnhancer (/home/ubuntu/workspace/node_modules/radium/lib/enhancer.js:85:26)
    at ReactCompositeComponentMixin.mountComponent (/home/ubuntu/workspace/node_modules/react/lib/ReactCompositeComponent.js:148:18)
    at wrapper [as mountComponent] (/home/ubuntu/workspace/node_modules/react/lib/ReactPerf.js:66:21)
    at /home/ubuntu/workspace/node_modules/react/lib/ReactServerRendering.js:42:38
    at ReactServerRenderingTransaction.Mixin.perform (/home/ubuntu/workspace/node_modules/react/lib/Transaction.js:136:20)
    at Object.renderToString (/home/ubuntu/workspace/node_modules/react/lib/ReactServerRendering.js:40:24)
    at Object.<anonymous> (/home/ubuntu/workspace/out.js:25:23)
    at Module._compile (module.js:399:26)
    at Object.Module._extensions..js (module.js:406:10)

Maybe this is only a problem with server side rendering? No export in that repro any way.

@ianobermiller
Copy link
Contributor

Ah, so the issue here is that the Radium enhancer class is compiled to ES5, which doesn't play nice when it tries to extend a native class. See also tvcutsem/harmony-reflect#55 and lodash/lodash#1193. Your only solution is to transpile your code before running in a newer version of node.

@GGAlanSmithee
Copy link
Author

Ah OK.. Makes sense.. Was hoping that I would not have to transpile server side (except for react and som unsupported es7 features) now that Node has gotten more es6 compatible. I guess I cab get away with only transpiling classes in this case. Do you know if this is likely to change in the future, so that es6 classes can be used with Radium?

@GGAlanSmithee
Copy link
Author

And thanks for taking your time to investigate this!

@GGAlanSmithee
Copy link
Author

confirmed that using babel-plugin-transform-es2015-classes solves the issue.

@ianobermiller
Copy link
Contributor

Since Radium overrides the render method, inheritance is the only mechanism
that allows this to work seamlessly. I'm certainly open to ideas, though!
On Tue, Dec 29, 2015 at 5:25 AM Alan Smithee notifications@github.com
wrote:

confirmed that using babel-plugin-transform-es2015-classes solves the
issue.


Reply to this email directly or view it on GitHub
#443 (comment)
.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants