Početna
» Osnovno znanje
»
Kako riješiti grešku "Module Not Found: Can’t Resolve fs" u Webpacku
Kako riješiti grešku "Module Not Found: Can’t Resolve fs" u Webpacku
Zadnja provjera: 11. rujna 2026. Greška “Module not found: Error: Can’t resolve 'fs'” obično znači da Webpack gradi kod za preglednik, ali vaš izvorni kod – ili jedna od njegovih ovisnosti – uvozi modul datotečnog sustava Node.js-a. Node dokumentira node:fs kao API za interakciju s datotečnim sustavom, dok trenutna Webpackova dokumentacija navodi da Webpack 5 više ne automatski polyfillira Node.js jezgrene module za buildove preglednika.
Ključni dio je odabir popravka koji odgovara onome što kod zapravo pokušava učiniti. Ne postoji jedna postavka koja je ispravna za svaki projekt. Ako vaša aplikacija doista treba čitati datoteke s diska poslužitelja, premjestite taj posao na Node/kod poslužitelja. Ako ovisnost uvozi fs samo za opcionalnu značajku koja radi samo u Node okruženju, a koju vaš bundle preglednika nikada ne koristi, resolve.fallback: { fs: false } može biti prikladno. Ako paket ima build kompatibilan s preglednikom, koristite to umjesto toga. A ako je bundle namijenjen pokretanju u Node okruženju, ciljajte Node umjesto da pretvarate da je riječ o web bundleu.
Brza tablica odluka
Situacija
Najbolji prvi popravak
Glavna prednost
Glavni kompromis
Vaš vlastiti kod preglednika uvozi fs
Uklonite ga iz putanje preglednika ili premjestite operaciju na poslužitelj/API
Odgovara stvarnom runtime okruženju
Zahtijeva arhitektonsku granicu između klijenta i poslužitelja
Ovisnost uvozi fs, ali ta značajka se nikada ne koristi u pregledniku
Razmotrite resolve.fallback: { fs: false }
Mala, jednostavna ispravka builda
Logički će zatajiti ako paket kasnije izvrši kod ovisan o datotečnom sustavu
Ovisnost nudi buildove za preglednik i Node
Koristite ili nadogradite na unos kompatibilan s preglednikom
Čuva namijenjeno ponašanje preglednika
Može zahtijevati promjene paketa/verzije
Izlaz se izvršava u Node okruženju, a ne u pregledniku
Koristite target: "node"
Zadržava Node ugrađene module dostupnima u runtimeu
Izlaz više nije bundle preglednika
Pokušavate “polyfillati fs” u pregledniku
Preispitajte zahtjev
Izbjegava zavaravajući sloj kompatibilnosti
Možda ćete trebati drugačiji tijek rada za pohranu/datoteke na strani preglednika
Webpackova službena dokumentacija za resolve.fallback navodi da Webpack 5 više ne polyfillira Node jezgrene module automatski. Njegove bilješke o izdanju Webpacka 5 objašnjavaju razlog: automatski polyfilli mogli su dodati veliki, nepotrebni kod za kompatibilnost u frontend bundleove, pa je Webpack prebacio odgovornost na autora aplikacije ili paketa.
Korak 1: Saznajte tko uvozi fs
Počnite s prvom korisnom linijom u Webpackovom izlazu grešaka. Ona obično pokazuje na datoteku u kojoj je rješavanje modula nije uspjelo, na primjer:
ERROR in ./src/utils/fileHelper.js 1:0-20
Module not found: Error: Can't resolve 'fs'
AI-generirana ilustracija Webpack builda koji ne uspijeva zbog uvoza fs. To nije izlaz iz stvarnog projekta; nazivi datoteka i brojevi linija su ilustrativni.
Ako je neuspjela datoteka vaša, pretražite je za bilo koji od ovih oblika:
const fs = require('fs')
// ili
import fs from 'node:fs'
// ili
import { readFile } from 'node:fs/promises'
Nodeova službena dokumentacija za datotečni sustav potvrđuje da su node:fs i node:fs/promises Node API-ji za operacije datotečnog sustava. Običan bundle preglednika ne dobiva pristup disku poslužitelja samo zato što Webpack može parsirati uvoz.
Ako je neuspjela datoteka unutar node_modules, nemojte odmah uređivati taj paket na mjestu. Prvo identificirajte koja je vršna ovisnost unijela tu datoteku u vaš bundle preglednika. Korisno pitanje nije samo “Koji paket uvozi fs?” već “Zašto je ta putanja koda orijentirana na Node dostupna iz mog klijentskog unosa?”
Koristite ovu dijagnozu kada: greška se pojavi nakon nadogradnje Webpacka, dodavanja ovisnosti, uvoza prethodno server-only utilityja u frontend kod ili premještanja zajedničkog koda u klijentski bundle.
Praktična provjera: privremeno uklonite uvoz koji vodi do neuspjele modula i ponovno izgradite. Ako fs greška nestane, potvrdili ste putanju ovisnosti prije promjene Webpackove konfiguracije.
Korak 2: Ako kod doista treba pristup datotečnom sustavu, premjestite ga na Node/kod poslužitelja
Ovo je najbolji popravak kada kod treba čitati konfiguracijske datoteke, predloške, lokalne dokumente, privatne ključeve, generirane resurse, zapise poslužitelja ili bilo što drugo s datotečnog sustava stroja.
Na primjer, ovo je prikladno u Node okruženju:
import { readFile } from 'node:fs/promises'
export async function loadTemplate() {
return readFile('./templates/email.html', 'utf8')
}
Ali to ne bi trebalo biti povučeno u unos preglednika. Umjesto toga, izložite rezultat kroz serverski sloj vaše aplikacije. Pojednostavljena podjela mogla bi biti:
// serverski kod
import { readFile } from 'node:fs/promises'
app.get('/api/template', async (req, res) => {
const text = await readFile('./templates/email.html', 'utf8')
res.type('text/plain').send(text)
})
// kod na strani preglednika
export async function loadTemplate() {
const response = await fetch('/api/template')
if (!response.ok) throw new Error('Failed to load template')
return response.text()
}
AI-generirana ilustracija odvajanja Node operacija datotečnog sustava od koda preglednika. To je primjer konceptualne arhitekture, a ne snimka zaslona specifičnog okvira.
Kompromis je arhitektonski: dodajete serversku krajnju točku ili drugu serversku granicu, ali čuvate semantiku fs-a. Preglednik zahtijeva podatke; poslužitelj čita datotečni sustav.
Ovo rješenje je prikladno kada: operacija datotečnog sustava je stvarna i potrebna.
Ovo rješenje nije potrebno kada: uvoz postoji samo unutar opcionalne Node putanje koda koju preglednik nikada ne izvršava. U tom slučaju, unos paketa specifičan za preglednik ili ignorirani fallback mogu biti čistiji.
Korak 3: Koristite resolve.fallback: { fs: false } samo kada je ponašanje datotečnog sustava opcionalno
Webpackov službeni vodič za migraciju s Webpacka 4 na 5 izričito navodi da konfiguracije koje koriste stari obrazac node.fs: 'empty' trebaju prijeći na:
AI-generirana ilustracija resolve.fallback: { fs: false }. Koristite ovo samo kada preglednik ne treba ponašanje datotečnog sustava ovisnosti.
Postavljanje fallbacka na false govori Webpacku da ne uključi implementaciju za taj neriješeni modul. To može biti točno ispravno za paket koji sadrži zaštićenu granicu koja radi samo u Node okruženju, poput koda koji koristi fs samo tijekom serverskog renderiranja ili izvršavanja CLI-ja.
To također može sakriti grešku builda dok vam ostavlja bug u dizajnu runtimea. Razmislite o ovoj ovisnosti:
Ako vaš preglednik stvarno poziva loadUserConfig(), zamjena fs-a s “ničim” ne stvara funkcionalni datotečni sustav preglednika. Build može napredovati, ali značajka i dalje ne može izvršiti namjeravanu Node operaciju.
Koristite fs: false kada: ste potvrdili da granica specifična za datotečni sustav nije korištena u web cilju.
Nemojte ga koristiti kada: vaša značajka preglednika ovisi o readFileSync, obilasku direktorija, serverskim putanjama ili drugom stvarnom Node ponašanju datotečnog sustava.
Zašto je “samo instalirajte fs polyfill” obično pogrešan prvi odgovor
Trenutna Webpackova dokumentacija za resolve.fallback daje primjere ručnih polyfila za nekoliko Node jezgrenih modula kao što su path, buffer, stream i crypto. Zanimljivo, njezin popis kompatibilnosti ne pruža opću zamjenu za fs ekvivalentnu Node datotečnom sustavu.
Ta razlika je važna. JavaScript utilityji se često mogu reproducirati u pregledniku. Proizvoljni pristup datotečnom sustavu hosta/poslužitelja je mogućnost runtimea, a ne samo nedostajuća pomoćna funkcija.
Ako vam stvarno treba tijek rada preglednika, odaberite dizajn nativan za preglednik za specifičan zadatak – na primjer, dohvatite resurs s URL-a, dopustite korisniku da odabere datoteku ili pohranite podatke aplikacije koristeći odgovarajući mehanizam pohrane preglednika. Ne procjenjujte uspjeh samo na temelju toga prestaje li Webpack prikazivati grešku.
Opcija 4: Preferirajte ovisnost kompatibilnu s preglednikom ili izvoz paketa
Ako greška dolazi od paketa treće strane, provjerite podržava li taj paket službeno preglednike. Trenutni Webpackov vodič za exports paketa objašnjava da paketi mogu pružiti uvjetne izvoze za okruženja kao što su browser i node. Webpackove smjernice za izdanje također preporučuju autorima paketa da pruže alternative kompatibilne s frontendom kada Node-only implementacije nisu prikladne za preglednike.
Ako nadograđena verzija paketa pruža pravi unos za preglednik dok vaša starija verzija ne pruža, nadogradnja može biti sigurnija od konfiguriranja fs: false. Isto tako, zamjena paketa orijentiranog na Node onim koji je eksplicitno dizajniran za korištenje u pregledniku može smanjiti hakove kompatibilnosti i složenost bundla.
Odaberite ovaj put kada: ovisnost bi trebala raditi u preglednicima, ali instalirana verzija bira ili izlaže implementaciju koja radi samo u Node okruženju.
Kompromis: nadogradnja ili zamjena paketa može uvesti promjene API-ja, pa pokrenite svoje uobičajene testove aplikacije umjesto da tretirate uspješan compile kao dovoljan.
Opcija 5: Ako je izlaz Node bundle, postavite cilj na Node
Ponekad Webpack uopće ne proizvodi kod preglednika. Možda bundleate CLI, pozadinskog radnika, alat za build, SSR poslužitelj ili Node servis. U tom slučaju, pokušaj suzbijanja fs-a je unatrag: runtime ga zapravo pruža.
se kompilira za okruženje slično Node.js-u i ostavlja ugrađene module kao što su fs i path da ih Node pruži u runtimeu.
Webpackova detaljnija referenca konfiguracije cilja također razlikuje web, node, Electron ciljeve, web radnike i druga okruženja.
Koristite target: 'node' kada: rezultirajući JavaScript će se izvršavati pod Node okruženjem.
Nemojte ga koristiti za “popravak” normalne SPA aplikacije preglednika: promjena cilja ne čini da preglednik odjednom pruža Node API-je datotečnog sustava. On mijenja okruženje za koje Webpack pretpostavlja da će izvršiti bundle.
Napredne Node buildove: externals mogu zadržati ugrađene module u runtimeu
Za serverske bundleove, Webpack također pruža ponašanje externals orijentirano na Node. Njegova službena dokumentacija za Externals navodi da externalsPresets.node može tretirati Node ugrađene module kao što su fs, path i vm kao eksterne i učitati ih s Node runtime require().
Tipična konfiguracija orijentirana na Node stoga bi mogla izgledati ovako:
Ovo je napredna briga za serverski bundle, a ne workaround za preglednik.
Korak 4: Ponovno izgradite, zatim testirajte značajku koja je uzrokovala uvoz
Nakon što napravite arhitektonsku ili konfiguracijsku promjenu, ponovno izgradite:
npm run build
AI-generirana ilustracija uspješne Webpack ponovne izgradnje. Brojevi verzija, veličine resursa i vremena builda su fiktivni primjeri.
Čist compile dokazuje samo da je rješavanje modula uspjelo. Ne dokazuje da se pogođena značajka ponaša ispravno. Testirajte prema popravku koji ste odabrali:
Ako ste premjestili pristup datotekama na poslužitelj, pozovite značajku preglednika i provjerite vraća li serverska krajnja točka očekivane podatke.
Ako ste postavili fs: false, isprobajte ovisnost u pregledniku i potvrdite da nikada ne ulazi u granicu ovisnu o datotečnom sustavu.
Ako ste prešli na build paketa za preglednik, pokrenite stvarni korisnički tijek rada paketa.
Ako ste promijenili cilj na Node, izvršite izgrađeni izlaz pod verzijom Nodea koju podržavate.
Usporedba uobičajenih popravaka
Popravak
Sigurno za preglednik?
Čuva stvarni pristup Node datotečnom sustavu?
Kada ga preferirati
Premjestite fs posao na poslužitelj/API
Da
Da, na poslužitelju
Vaša aplikacija doista treba podatke datotečnog sustava poslužitelja
resolve.fallback.fs = false
Samo ako fs granica nije korištena
Ne
Opcionalna putanja ovisnosti koja radi samo u Node okruženju
Paket/izvoz specifičan za preglednik
Da, ako paket to podržava
Ne; pruža ponašanje specifično za preglednik umjesto toga
Ovisnost je namijenjena podršci oba runtimea
target: 'node'
Ne
Da
Bundle se zapravo izvršava u Node okruženju
Generički “fs polyfill”
Ovisi o biblioteci i semantici
Nije ekvivalentno proizvoljnom pristupu Node datotečnom sustavu
Samo nakon provjere točnog ponašanja preglednika koje trebate
Specijalni slučaj: zajednički kod uvezen od strane bundleova preglednika i poslužitelja
Čest izvor ove greške je utility modul koji sadrži i čiste funkcije i pomoćne funkcije koje rade samo u Node okruženju:
// shared-utils.js
import fs from 'node:fs'
export function formatDate(date) {
return new Intl.DateTimeFormat('en-US').format(date)
}
export function readConfig(path) {
return fs.readFileSync(path, 'utf8')
}
Čak i ako vaš preglednik uvozi samo formatDate, uvoz fs na vrhu može prisiliti Webpack da riješi fs. Čistiji dizajn je podijeliti module:
// shared/formatDate.js
export function formatDate(date) {
return new Intl.DateTimeFormat('en-US').format(date)
}
// server/readConfig.js
import fs from 'node:fs'
export function readConfig(path) {
return fs.readFileSync(path, 'utf8')
}
Ovo čini granicu runtimea vidljivom u grafu modula umjesto da se oslanja na tree-shaking ili fallback za uklanjanje nekompatibilnog uvoza.
Specijalni slučaj: greška se pojavila nakon nadogradnje s Webpacka 4
Ovo je jedan od klasičnih simptoma migracije na Webpack 5. Webpack 4 automatski je isporučivao shims za kompatibilnost za mnoge Node jezgrene module. Webpack 5 je namjerno prestao to raditi. Ako je vaš kod “radio prije nadogradnje”, pitajte je li doista trebao Node značajku u pregledniku ili je stari bundler tiho ubrizgavao kod za kompatibilnost.
Službeni Webpack vodič za migraciju preporučuje čitanje smjernica o breaking changeovima u izlazu greške builda i zamjenu stare node.* konfiguracije kompatibilnosti novijim pristupom resolvera gdje je prikladno.
Nemojte pretpostavljati da je ponovno stvaranje svakog Webpack 4 polyfila najbolja migracija. Webpackove vlastite bilješke o izdanju preporučuju module kompatibilne s frontendom gdje je moguće.
Konačna samoprovjera
Prije zatvaranja problema, provjerite ove točke:
Pronađite točnu izvornu datoteku ili ovisnost koja uvozi fs.
Potvrdite izvršava li se pogođeni bundle u pregledniku ili u Node okruženju.
Ako je riječ o bundleu preglednika, provjerite treba li značajka doista ponašanje datotečnog sustava.
Ako treba, premjestite operaciju datotečnog sustava iza serverske granice.
Ako je korištenje fs-a ovisnosti opcionalno i nikada se ne izvršava u pregledniku, razmotrite resolve.fallback: { fs: false }.
Ako paket službeno pruža izvoz za preglednik, preferirajte to umjesto suzbijanja potrebnog ponašanja.
Ako se bundle izvršava u Node okruženju, koristite Node cilj umjesto web cilja.
Ponovno izgradite i potvrdite da je greška rješavanja modula nestala.
Pokrenite stvarnu značajku koja je prethodno povukla fs; nemojte stati na “compiled successfully”.
Trajni popravak je usklađivanje koda s njegovim runtimeom. fs pripada okruženju datotečnog sustava Nodea. Webpack 5 čini tu granicu vidljivijom time što više ne ubrizgava Node jezgrene polyfile automatski. Jednom kada odlučite pripada li posao datotečnog sustava poslužitelju, je li opcionalan u pregledniku ili je dio bundlea ciljanog na Node, ispravna konfiguracija postaje mnogo lakša za odabrati.