{"record":{"id":"1cb9d3c978bcf96e","repo":"parcel-bundler/parcel","slug":"emfile","errorCode":"EMFILE","errorMessage":"EMFILE: ${path} no available file descriptor","messagePattern":"EMFILE: (.+?) no available file descriptor","errorType":"exception","errorClass":"FSError","httpStatus":null,"severity":"error","filePath":"packages/dev/repl/src/parcel/ExtendedMemoryFS.js","lineNumber":267,"sourceCode":"    throw new FSError('ENOENT', path.dirname(oldPath), \"wasn't found\");\n  }\n\n  _nextFD(path: FilePath): number {\n    let tested = 0;\n    let fd;\n    while (tested < FD_MAX) {\n      let candidate = this.nextFD++;\n      if (candidate >= FD_MAX) {\n        this.nextFD = 1;\n        candidate = this.nextFD++;\n      }\n      if (!this.openFDs.has(candidate)) {\n        fd = candidate;\n        break;\n      }\n    }\n    if (!fd) {\n      throw new FSError('EMFILE', path, 'no available file descriptor');\n    }\n    return fd;\n  }\n\n  openSync(filePath: FilePath, flags: number, mode: number): number {\n    flags = parseOpenFlags(flags);\n    if (flags & CONSTANTS.O_NOFOLLOW && this.symlinks.has(filePath)) {\n      throw new FSError('ELOOP', filePath, 'is a symlink');\n    }\n\n    filePath = this._normalizePath(filePath);\n\n    let file = this.files.get(filePath);\n    if (flags & CONSTANTS.O_CREAT) {\n      if (file) {\n        if (flags & CONSTANTS.O_EXCL) {\n          throw new FSError('EEXIST', filePath, 'already exists');\n        }","sourceCodeStart":249,"sourceCodeEnd":285,"githubUrl":"https://github.com/parcel-bundler/parcel/blob/59484858a1a0bcbb71f74088956bb437a2db6505/packages/dev/repl/src/parcel/ExtendedMemoryFS.js#L249-L285","documentation":"EMFILE raised by `ExtendedMemoryFS._nextFD` when the in-memory FS has `FD_MAX` open file descriptors and none are free. This is a descriptor leak: opens without matching closes exhaust the table.","triggerScenarios":"Repeated `openSync` without `closeSync`, exceeding FD_MAX; a transformer/packager that opens many files concurrently and forgets to close them.","commonSituations":"Long-running REPL sessions that accumulate handles; bulk operations opening many assets; missing `fs.closeSync(fd)` after reads/writes.","solutions":["Ensure every successful `openSync` is paired with `closeSync` in a finally block.","Limit concurrent opens with a small pool/queue.","If FD_MAX is genuinely too low for your workload, raise it in the FS config — but a leak is the more likely cause."],"exampleFix":"// before\nconst fd = fs.openSync(p, O_RDONLY);\nuse(fs.readSync(fd, ...));\n// after\nconst fd = fs.openSync(p, O_RDONLY);\ntry { use(fs.readSync(fd, ...)); }\nfinally { fs.closeSync(fd); }","handlingStrategy":"try-catch","validationCode":"function assertFDFree(fs) {\n  // expose openFDs size; fail fast before openSync if near FD_MAX\n  if (fs.openFDs.size >= FD_MAX) throw new Error('FD table full — close handles');\n}","typeGuard":null,"tryCatchPattern":"let fd;\ntry { fd = fs.openSync(p, flags); /* ... */ }\nfinally { if (fd != null) fs.closeSync(fd); }","preventionTips":["Always pair openSync with closeSync in a finally block.","Bound concurrent opens with a pool.","Treat EMFILE as a leak signal, not a capacity ceiling."],"tags":["filesystem","memory-fs","file-descriptors","emfile","resource-leak","repl"],"backgroundTag":null,"analyzedSha":"59484858a1a0bcbb71f74088956bb437a2db6505","analyzedAt":"2026-08-13T04:06:35.925Z","schemaVersion":2},"datasetVersion":"2026-08-13T04:17:16.726Z"}