Hawkbat / VTubeStudioJS

An implementation of the VTube Studio API for Node and browser JS
MIT License
45 stars 2 forks source link

Make ws an optional peer dependency #11

Closed adarah closed 1 year ago

adarah commented 1 year ago

Hi, I've been using this library in a plugin I'm developing and it's working nicely, but I have been having trouble getting it to be bundled correctly for the browser/edge runtimes in some situations.

When this library is paired with some other library which depends on ws (in my case, the other library depends on isomorphic-ws which uses ws as a peer dependency), the bundler ends up attempting to include node-specific code in the final output.

Situations that happened to me:

  1. In Next.js, webpack tries to ship the ws package to the browser.
  2. In Sveltekit, when trying to build for an edge runtime such as Cloudflare workers, the final bundle attempts to include ws, which fails the build.

For problem 1 I've managed to avoid it by using this hack:

// next.config.js
 webpack: (config) => {
    // Prevent the vtubestudio package from requiring ws in the browser and in the edge-runtime.
    const ignorePlug = new webpack.IgnorePlugin({ resourceRegExp: /^ws$/, contextRegExp: /vtubestudio\/lib/ })
    config.plugins.push(ignorePlug)
    return config
  },

But for problem 2, I couldn't figure out a way to make vite ignore that module.

In any case, the best solution to these issues is to simply not require ws in this package. This should be fine as you already provide a way for users to supply their own WebSocket implementation. I'm not super confident how they work, but I believe you should probably also mark ws as an optional peer dependency.

Hawkbat commented 1 year ago

Good call-out. I intended it to be an optional dependency precisely for this use case, but I didn't realize that webpack/vite would see the require('ws') line and still try to resolve it. I think you're right about making it a peer dependency; I'll play around with it and see if I can get that fixed.

Hawkbat commented 1 year ago

I've fixed this in v3.2.0. Unfortunately using peer dependencies did not solve the issue of Vite attempting to resolve the ws model, so for now I've removed the import entirely. In non-browser environments, the WebSocket implementation must be passed in explicitly via the webSocketFactory option.