diff --git a/src/node_file.cc b/src/node_file.cc index 44b4d4595e4455..4443f4be8697f8 100644 --- a/src/node_file.cc +++ b/src/node_file.cc @@ -3245,8 +3245,8 @@ static void CpSyncCheckPaths(const FunctionCallbackInfo& args) { errorno, dereference ? "stat" : "lstat", nullptr, src.out()); } auto dest_status = - dereference ? std::filesystem::symlink_status(dest_path, error_code) - : std::filesystem::status(dest_path, error_code); + dereference ? std::filesystem::status(dest_path, error_code) + : std::filesystem::symlink_status(dest_path, error_code); bool dest_exists = !error_code && dest_status.type() != std::filesystem::file_type::not_found; diff --git a/test/known_issues/test-fs-cp-sync-dereference.js b/test/known_issues/test-fs-cp-sync-dereference.js deleted file mode 100644 index fbb07a8f781520..00000000000000 --- a/test/known_issues/test-fs-cp-sync-dereference.js +++ /dev/null @@ -1,39 +0,0 @@ -'use strict'; - -// Refs: https://github.com/nodejs/node/issues/58939 -// -// The cpSync function is not correctly handling the `dereference` option. -// In this test, both the cp and cpSync functions are attempting to copy -// a file over a symlinked directory. In the cp case it works fine. In the -// cpSync case it fails with an error. - -const common = require('../common'); - -const { - cp, - cpSync, - mkdirSync, - symlinkSync, - writeFileSync, -} = require('fs'); - -const { - join, -} = require('path'); - -const tmpdir = require('../common/tmpdir'); -tmpdir.refresh(); - -const pathA = join(tmpdir.path, 'a'); -const pathB = join(tmpdir.path, 'b'); -const pathC = join(tmpdir.path, 'c'); -const pathD = join(tmpdir.path, 'd'); - -writeFileSync(pathA, 'file a'); -mkdirSync(pathB); -symlinkSync(pathB, pathC, 'dir'); -symlinkSync(pathB, pathD, 'dir'); - -cp(pathA, pathD, { dereference: false }, common.mustSucceed()); - -cpSync(pathA, pathC, { dereference: false }); diff --git a/test/parallel/test-fs-cp-sync-dereference.js b/test/parallel/test-fs-cp-sync-dereference.js new file mode 100644 index 00000000000000..dffb5b171c4d1d --- /dev/null +++ b/test/parallel/test-fs-cp-sync-dereference.js @@ -0,0 +1,50 @@ +'use strict'; + +// Refs: https://github.com/nodejs/node/issues/58939 +// +// In this test, both the cp and cpSync functions are attempting to copy +// a file over a symlinked directory. + +const common = require('../common'); + +const { + cp, + cpSync, + mkdirSync, + symlinkSync, + writeFileSync, + readFileSync, + statSync +} = require('fs'); + +const { + join, +} = require('path'); + +const assert = require('assert'); + +const tmpdir = require('../common/tmpdir'); +tmpdir.refresh(); + +const pathA = join(tmpdir.path, 'a'); // file +const pathB = join(tmpdir.path, 'b'); // directory +const pathC = join(tmpdir.path, 'c'); // c -> b +const pathD = join(tmpdir.path, 'd'); // d -> b + +writeFileSync(pathA, 'file a'); +mkdirSync(pathB); +symlinkSync(pathB, pathC, 'dir'); +symlinkSync(pathB, pathD, 'dir'); + +cp(pathA, pathD, { dereference: false }, common.mustSucceed(() => { + // The path d is now a file, not a symlink + assert.strictEqual(readFileSync(pathA, 'utf-8'), readFileSync(pathD, 'utf-8')); + assert.ok(statSync(pathA).isFile()); + assert.ok(statSync(pathD).isFile()); +})); + +cpSync(pathA, pathC, { dereference: false }); + +assert.strictEqual(readFileSync(pathA, 'utf-8'), readFileSync(pathC, 'utf-8')); +assert.ok(statSync(pathA).isFile()); +assert.ok(statSync(pathC).isFile());