From 8e86f02c4316a040a102869a457366f3634a8b8a Mon Sep 17 00:00:00 2001 From: Brian Gough Date: Thu, 7 May 2020 10:30:14 +0100 Subject: [PATCH] set encoding when reading from streams using .toString() works most of the time but can lead to utf8 characters being broken across chunk boundaries. https://nodejs.org/api/stream.html#stream_readable_setencoding_encoding --- services/clsi/app/js/CompileManager.js | 2 +- services/clsi/app/js/LocalCommandRunner.js | 2 +- services/clsi/app/js/OutputFileFinder.js | 2 +- services/clsi/app/js/OutputFileOptimiser.js | 2 +- services/clsi/test/unit/js/CompileManagerTests.js | 2 ++ services/clsi/test/unit/js/OutputFileFinderTests.js | 1 + 6 files changed, 7 insertions(+), 4 deletions(-) diff --git a/services/clsi/app/js/CompileManager.js b/services/clsi/app/js/CompileManager.js index 3bf54bc75b..dd62f435ed 100644 --- a/services/clsi/app/js/CompileManager.js +++ b/services/clsi/app/js/CompileManager.js @@ -334,7 +334,7 @@ module.exports = CompileManager = { proc.on('error', callback) let stderr = '' - proc.stderr.on('data', chunk => (stderr += chunk.toString())) + proc.stderr.setEncoding('utf8').on('data', chunk => (stderr += chunk)) return proc.on('close', function(code) { if (code === 0) { diff --git a/services/clsi/app/js/LocalCommandRunner.js b/services/clsi/app/js/LocalCommandRunner.js index 61ecd88794..ccaf50784a 100644 --- a/services/clsi/app/js/LocalCommandRunner.js +++ b/services/clsi/app/js/LocalCommandRunner.js @@ -46,7 +46,7 @@ module.exports = CommandRunner = { const proc = spawn(command[0], command.slice(1), { cwd: directory, env }) let stdout = '' - proc.stdout.on('data', data => (stdout += data)) + proc.stdout.setEncoding('utf8').on('data', data => (stdout += data)) proc.on('error', function(err) { logger.err( diff --git a/services/clsi/app/js/OutputFileFinder.js b/services/clsi/app/js/OutputFileFinder.js index 50012b51b7..831997811b 100644 --- a/services/clsi/app/js/OutputFileFinder.js +++ b/services/clsi/app/js/OutputFileFinder.js @@ -87,7 +87,7 @@ module.exports = OutputFileFinder = { const proc = spawn('find', args) let stdout = '' - proc.stdout.on('data', chunk => (stdout += chunk.toString())) + proc.stdout.setEncoding('utf8').on('data', chunk => (stdout += chunk)) proc.on('error', callback) return proc.on('close', function(code) { if (code !== 0) { diff --git a/services/clsi/app/js/OutputFileOptimiser.js b/services/clsi/app/js/OutputFileOptimiser.js index c0b8cc141a..41ba7b40c3 100644 --- a/services/clsi/app/js/OutputFileOptimiser.js +++ b/services/clsi/app/js/OutputFileOptimiser.js @@ -78,7 +78,7 @@ module.exports = OutputFileOptimiser = { const timer = new Metrics.Timer('qpdf') const proc = spawn('qpdf', args) let stdout = '' - proc.stdout.on('data', chunk => (stdout += chunk.toString())) + proc.stdout.setEncoding('utf8').on('data', chunk => (stdout += chunk)) callback = _.once(callback) // avoid double call back for error and close event proc.on('error', function(err) { logger.warn({ err, args }, 'qpdf failed') diff --git a/services/clsi/test/unit/js/CompileManagerTests.js b/services/clsi/test/unit/js/CompileManagerTests.js index 180f6f311f..74a0a47fff 100644 --- a/services/clsi/test/unit/js/CompileManagerTests.js +++ b/services/clsi/test/unit/js/CompileManagerTests.js @@ -294,6 +294,7 @@ describe('CompileManager', function() { this.proc = new EventEmitter() this.proc.stdout = new EventEmitter() this.proc.stderr = new EventEmitter() + this.proc.stderr.setEncoding = sinon.stub().returns(this.proc.stderr) this.child_process.spawn = sinon.stub().returns(this.proc) this.CompileManager.clearProject( this.project_id, @@ -328,6 +329,7 @@ describe('CompileManager', function() { this.proc = new EventEmitter() this.proc.stdout = new EventEmitter() this.proc.stderr = new EventEmitter() + this.proc.stderr.setEncoding = sinon.stub().returns(this.proc.stderr) this.child_process.spawn = sinon.stub().returns(this.proc) this.CompileManager.clearProject( this.project_id, diff --git a/services/clsi/test/unit/js/OutputFileFinderTests.js b/services/clsi/test/unit/js/OutputFileFinderTests.js index e5f990466e..ee591b408d 100644 --- a/services/clsi/test/unit/js/OutputFileFinderTests.js +++ b/services/clsi/test/unit/js/OutputFileFinderTests.js @@ -70,6 +70,7 @@ describe('OutputFileFinder', function() { beforeEach(function() { this.proc = new EventEmitter() this.proc.stdout = new EventEmitter() + this.proc.stdout.setEncoding = sinon.stub().returns(this.proc.stdout) this.spawn.returns(this.proc) this.directory = '/base/dir' return this.OutputFileFinder._getAllFiles(this.directory, this.callback)