Skip to content

Commit 7d156cc

Browse files
committed
vfs: normalize RealFSProvider mkdir return paths
RealFSProvider.mkdirSync()/mkdir() forwarded the raw fs.mkdirSync() result, which for { recursive: true } is the absolute backing-directory path of the first created directory. VirtualFileSystem#toMountedPath() then joined the mount point with it, producing <mount>/<root>/a instead of <mount>/a, so the returned path failed fs.existsSync(). Reuse the existing #resolvedToVfsPath() helper (as realpath does) to translate the result back to a provider-relative VFS path, matching MemoryProvider. Signed-off-by: Kamat, Trivikram <16024985+trivikr@users.noreply.github.com> Assisted-by: opencode
1 parent 3cd2d6e commit 7d156cc

3 files changed

Lines changed: 50 additions & 2 deletions

File tree

‎lib/internal/vfs/providers/real.js‎

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -458,12 +458,16 @@ class RealFSProvider extends VirtualProvider {
458458

459459
mkdirSync(vfsPath, options) {
460460
const realPath = this.#resolvePath(vfsPath);
461-
return fs.mkdirSync(realPath, options);
461+
const created = fs.mkdirSync(realPath, options);
462+
if (created === undefined) return undefined;
463+
return this.#resolvedToVfsPath(created, vfsPath, 'mkdir');
462464
}
463465

464466
async mkdir(vfsPath, options) {
465467
const realPath = this.#resolvePath(vfsPath);
466-
return fs.promises.mkdir(realPath, options);
468+
const created = await fs.promises.mkdir(realPath, options);
469+
if (created === undefined) return undefined;
470+
return this.#resolvedToVfsPath(created, vfsPath, 'mkdir');
467471
}
468472

469473
rmdirSync(vfsPath) {

‎test/parallel/test-vfs-real-provider-promises.js‎

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,19 @@ const myVfs = vfs.create(new vfs.RealFSProvider(root));
3535
assert.deepStrictEqual(entries.sort(), ['sub']);
3636
await myVfs.promises.rmdir('/d/sub');
3737

38+
// Recursive mkdir returns the first directory created, as a VFS-relative
39+
// path (never the backing-directory path), matching MemoryProvider.
40+
const createdSub = await myVfs.promises.mkdir('/d/sub', { recursive: true });
41+
assert.strictEqual(createdSub, '/d/sub');
42+
assert.strictEqual(await myVfs.promises.mkdir('/d/sub', { recursive: true }),
43+
undefined);
44+
const created = await myVfs.promises.mkdir('/d/deep/nested', { recursive: true });
45+
assert.strictEqual(created, '/d/deep');
46+
assert.strictEqual(myVfs.existsSync(created), true);
47+
await myVfs.promises.rmdir('/d/sub');
48+
await myVfs.promises.rmdir('/d/deep/nested');
49+
await myVfs.promises.rmdir('/d/deep');
50+
3851
// rename
3952
await myVfs.promises.writeFile('/old.txt', 'x');
4053
await myVfs.promises.rename('/old.txt', '/new.txt');

‎test/parallel/test-vfs-real-provider.js‎

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -106,6 +106,37 @@ fs.mkdirSync(testDir, { recursive: true });
106106
fs.rmdirSync(path.join(testDir, 'deep/nested/dir'));
107107
fs.rmdirSync(path.join(testDir, 'deep/nested'));
108108
fs.rmdirSync(path.join(testDir, 'deep'));
109+
110+
// Recursive mkdir returns the first directory created, as a VFS-relative
111+
// path (never the backing-directory path), matching MemoryProvider.
112+
const created = realVfs.mkdirSync('/returned/nested/dir', { recursive: true });
113+
assert.strictEqual(created, '/returned');
114+
assert.strictEqual(realVfs.existsSync(created), true);
115+
assert.strictEqual(
116+
realVfs.mkdirSync('/returned/nested/dir', { recursive: true }),
117+
undefined,
118+
);
119+
assert.strictEqual(realVfs.mkdirSync('/returned/new-dir'),
120+
undefined);
121+
fs.rmdirSync(path.join(testDir, 'returned/nested/dir'));
122+
fs.rmdirSync(path.join(testDir, 'returned/nested'));
123+
fs.rmdirSync(path.join(testDir, 'returned/new-dir'));
124+
fs.rmdirSync(path.join(testDir, 'returned'));
125+
}
126+
127+
// Mounted recursive mkdir returns a path that exists on the real filesystem.
128+
{
129+
const realVfs = vfs.create(new vfs.RealFSProvider(testDir));
130+
const mountPoint = realVfs.mount();
131+
try {
132+
const created = realVfs.mkdirSync(path.join(mountPoint, 'm/nested/dir'),
133+
{ recursive: true });
134+
assert.strictEqual(created, path.join(mountPoint, 'm'));
135+
assert.strictEqual(fs.existsSync(created), true);
136+
} finally {
137+
realVfs.unmount();
138+
fs.rmSync(path.join(testDir, 'm'), { recursive: true, force: true });
139+
}
109140
}
110141

111142
// unlink

0 commit comments

Comments
 (0)