vasturiano / 3d-force-graph

3D force-directed graph component using ThreeJS/WebGL
https://vasturiano.github.io/3d-force-graph/example/large-graph/
MIT License
4.5k stars 803 forks source link

Commonjs incompatibility #423

Open rubybrowncoat opened 3 years ago

rubybrowncoat commented 3 years ago

Describe the bug The currently built .common.js asset is not compatible with commonjs because of its dependencies (namely the threejs example modules loaded from the jsm directory both inside the main project and in its three-render-objects dependency)

There exists a similar issue on the 2d version force-graph with another library (bezier-js), that projects however has a recent compatible released version because the affected change in the dependency is behind a version excluded by the earlier package.js. In this project, the three-render-objects dependency is loaded in such a way that it is always satisfying the latest version so I haven't found a recent compatible version to backtrack to. One would have to go back to at least 1.29.2 to find a version without the incompatible dependency. And that version is not working for other reasons so I am kinda stuck on this.

To Reproduce Cannot use the module in commonjs, even if it does expose a .common.js built asset.

Expected behavior The commonjs built asset shouldn't contain commonjs incompatible statements (import and related behaviour is the main culprit, as usual)

vasturiano commented 3 years ago

@rubybrowncoat thanks for reaching out.

Yes, this is a tricky issue to fix. The cause of the problem is the way Three.js exposes required components from the examples folder, such as TrackballControls for example: https://github.com/mrdoob/three.js/blob/dev/examples/jsm/controls/TrackballControls.js#L1-L7

These modules need to be deep linked as there's no top level entrypoint for them in the package. And there are only ES modules versions (jsm) and a variant relying on globals (js), which is actually soon to be deprecated.

All this introduces issues for consuming modules that wish to expose commonJs entry points.

I'm not quite sure how to get around this, but I suspect I might be forced to drop the support for commonJs on 3d-force-graph for this reason.

Worth seeing also the ThreeJs docs on commonJs, namely this section:

Second, Node.js support for ES modules is ... complicated. As of Node.js v12, the core library can be imported as a CommonJS module, with require('three'). However, most example components in examples/jsm cannot. Future versions of Node.js may resolve this, but in the meantime you may need to use workarounds like esm to enable your Node.js application to recognize ES modules.