The only thing which I believe is still needed is a bundler when your project grows to a certain size. Fetching a complex graph of thousands of files will likely never be fast.
Using webpack resulted in some of the most painful experiences of supporting serious production software in my career.
The progress and maturity of JS tooling/DX as a result of stuff like esbuild and Vite, or Typescript more generally, can not he understated.
For people not doing frontend it can seem like a neverending series of new stuff but there is a very rational and tangible level of progress being made. Especially for serious JS devs not jumping on hype trains.
I don't miss the days of gulp and webpack at all and I don't blame anyone for hating on JS if they experienced using them professionally.
I never invested too much time in understanding webpack but it does feel like fighting it a lot of the time when I want to change something in my personal projects.
Care to share some anecdotes of those painful experiences?
Now Vite seems to be all the rage? But is it a bundler?
Wepack seems to be very hard to configure. Looks like nginx config vs caddy config.
Rather, one would opt for something like vite, the spiritual successor to react-scripts, that bundles all of these tools together with some good defaults/plugins, a means to configure them, and usually also some kind of dev server with hot module reloading, for a complete developer experience using your preferred toolchain.
Check out 'parcel' for something pretty modern, universal, and low effort, IMHO.
And a type system... And maybe a styling system... Oh and let's have some nice Rx data flows!
But, jokes aside, even if you go that Route you still end up with a complex npm project that involves dozens of libraries.
I've been at that point every year since starting doing npm spas in 2014ish (mostly as side projects, my work is typically more serverside). At some point I just decided that the upkeep wasn't worth it any more as you create the same stack every year but with wildly different libs. For me the solution was to switch to an elm+sass+webpack boilerplate that hasn't changed since 2018 or there abouts.
A lot of this JavaScript criticism was appropriate circa 2017, but these days JavaScript's gotten a lot more stable.
ES2015 was the one big language update, and although it took a while to all roll out and for older browsers to die off, at this point we’re now living in “the future” and almost all language changes are incremental.
Like, you can write ES modules with async/await and run it in all modern browsers without any compilation. If you add an HTML import-map element you can even import node_modules by name.
Now, most people still prefer to use a bundler so that their users can load a single script instead of dozens of tiny ones, but that’s optional, and the gap between “the code you write” and “code that runs in the browser” hasn’t been this small in years.
Not everyone is on a greenfield project with full authority to grab the freshest and latest. Some of us are effectively living in 2014-- they can't say "no, you can't use IE11" to paying customers, or committed to a platform at the wrong phase of maturity, and remain stuck around a state-of-the-art-in-2014 build process.
You write fantasy future JavaScript. Sure, it will be available in ECMAScript 23, scheduled to drop in real browsers in 2092. But for now, here's a convoluted mess of polyfills, Babel, and WebPack, that we HOPE papers over the real behaviour of browsers, and suddenly your test-and-debug cycle has introduced a flow-shattering 15-second build cycle each time you change a file.