From 8477267b91e9f3bc678aea12ad223a28a9dd899e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?H=C3=BCseyin=20A=C3=A7acak?= Date: Tue, 5 Mar 2024 16:38:03 +0300 Subject: [PATCH 1/2] lib: print Python executable path using UTF-8 The Python executable path may have non-ASCII characters, which can make the print function fail if the environment encoding is different. This fixes this issue by using stdout.buffer, which can be used with UTF-8 encoding for the output, regardless of the environment encoding. Fixes: https://github.com/nodejs/node-gyp/issues/2829 --- lib/find-python.js | 2 +- test/test-find-python.js | 15 +++++++++++++++ 2 files changed, 16 insertions(+), 1 deletion(-) diff --git a/lib/find-python.js b/lib/find-python.js index 615da57bb8..a71c00c2b6 100644 --- a/lib/find-python.js +++ b/lib/find-python.js @@ -41,7 +41,7 @@ class PythonFinder { static findPython = (...args) => new PythonFinder(...args).findPython() log = log.withPrefix('find Python') - argsExecutable = ['-c', 'import sys; print(sys.executable);'] + argsExecutable = ['-c', 'import sys; sys.stdout.buffer.write(sys.executable.encode(\'utf-8\'));'] argsVersion = ['-c', 'import sys; print("%s.%s.%s" % sys.version_info[:3]);'] semverRange = '>=3.6.0' diff --git a/test/test-find-python.js b/test/test-find-python.js index c5fa35d4bc..b3bf3e7d8c 100644 --- a/test/test-find-python.js +++ b/test/test-find-python.js @@ -7,6 +7,9 @@ const assert = require('assert') const PythonFinder = require('../lib/find-python') const { execFile } = require('../lib/util') const { poison } = require('./common') +const fs = require('fs') +const path = require('path') +const os = require('os') class TestPythonFinder extends PythonFinder { constructor (...args) { @@ -32,6 +35,18 @@ describe('find-python', function () { assert.strictEqual(stderr, '') }) + it('find python - encoding', async function () { + const found = await PythonFinder.findPython(null) + const testFolderPath = fs.mkdtempSync(path.join(os.tmpdir(), 'test-ü-')) + const testFilePath = path.join(testFolderPath, 'python.exe') + fs.copyFileSync(found, testFilePath) + + const foundTest = await PythonFinder.findPython(testFilePath) + fs.unlinkSync(testFilePath) + fs.rmdirSync(testFolderPath) + assert.strictEqual(foundTest, testFilePath) + }) + it('find python - python', async function () { const f = new TestPythonFinder('python') f.execFile = async function (program, args, opts) { From c2536aa44ef85362c3d9622aede4ed874adf54ed Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?H=C3=BCseyin=20A=C3=A7acak?= Date: Tue, 12 Mar 2024 17:16:32 +0300 Subject: [PATCH 2/2] fixup! lib: print Python executable path using UTF-8 --- test/test-find-python.js | 26 ++++++++++++++++++++------ 1 file changed, 20 insertions(+), 6 deletions(-) diff --git a/test/test-find-python.js b/test/test-find-python.js index b3bf3e7d8c..dc7192809a 100644 --- a/test/test-find-python.js +++ b/test/test-find-python.js @@ -2,7 +2,7 @@ delete process.env.PYTHON -const { describe, it } = require('mocha') +const { describe, it, after } = require('mocha') const assert = require('assert') const PythonFinder = require('../lib/find-python') const { execFile } = require('../lib/util') @@ -39,12 +39,26 @@ describe('find-python', function () { const found = await PythonFinder.findPython(null) const testFolderPath = fs.mkdtempSync(path.join(os.tmpdir(), 'test-ü-')) const testFilePath = path.join(testFolderPath, 'python.exe') - fs.copyFileSync(found, testFilePath) + after(function () { + try { + fs.unlinkSync(testFilePath) + fs.rmdirSync(testFolderPath) + } catch {} + }) - const foundTest = await PythonFinder.findPython(testFilePath) - fs.unlinkSync(testFilePath) - fs.rmdirSync(testFolderPath) - assert.strictEqual(foundTest, testFilePath) + try { + fs.symlinkSync(found, testFilePath) + } catch (err) { + switch (err.code) { + case 'EPERM': + return assert.fail(err, null, 'Please try to run console as an administrator') + default: + return assert.fail(err) + } + } + + const finder = new PythonFinder(testFilePath) + await assert.doesNotReject(finder.checkCommand(testFilePath)) }) it('find python - python', async function () {