From e1a358837f4c775dedc065ff9f16794a00fc31ec Mon Sep 17 00:00:00 2001 From: Ruben Bridgewater Date: Sun, 31 May 2020 18:23:07 +0200 Subject: [PATCH] util: improve getStringWidth performance MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This makes sure the common path does not normalize the input string. It's only required for characters that are outside of the ASCII range. Signed-off-by: Ruben Bridgewater PR-URL: https://github.com/nodejs/node/pull/33674 Reviewed-By: Anna Henningsen Reviewed-By: James M Snell Reviewed-By: Tobias Nießen Reviewed-By: Anto Aravinth --- lib/internal/util/inspect.js | 16 ++++++---------- 1 file changed, 6 insertions(+), 10 deletions(-) diff --git a/lib/internal/util/inspect.js b/lib/internal/util/inspect.js index a85726ce152a42..fdd70802a8e55e 100644 --- a/lib/internal/util/inspect.js +++ b/lib/internal/util/inspect.js @@ -1953,13 +1953,6 @@ function formatWithOptions(inspectOptions, ...args) { return str; } -function prepareStringForGetStringWidth(str, removeControlChars) { - str = str.normalize('NFC'); - if (removeControlChars) - str = stripVTControlCharacters(str); - return str; -} - if (internalBinding('config').hasIntl) { const icu = internalBinding('icu'); // icu.getStringWidth(string, ambiguousAsFullWidth, expandEmojiSequence) @@ -1970,13 +1963,14 @@ if (internalBinding('config').hasIntl) { getStringWidth = function getStringWidth(str, removeControlChars = true) { let width = 0; - str = prepareStringForGetStringWidth(str, removeControlChars); + if (removeControlChars) + str = stripVTControlCharacters(str); for (let i = 0; i < str.length; i++) { // Try to avoid calling into C++ by first handling the ASCII portion of // the string. If it is fully ASCII, we skip the C++ part. const code = str.charCodeAt(i); if (code >= 127) { - width += icu.getStringWidth(str.slice(i)); + width += icu.getStringWidth(str.slice(i).normalize('NFC')); break; } width += code >= 32 ? 1 : 0; @@ -1990,7 +1984,9 @@ if (internalBinding('config').hasIntl) { getStringWidth = function getStringWidth(str, removeControlChars = true) { let width = 0; - str = prepareStringForGetStringWidth(str, removeControlChars); + if (removeControlChars) + str = stripVTControlCharacters(str); + str = str.normalize('NFC'); for (const char of str) { const code = char.codePointAt(0); if (isFullWidthCodePoint(code)) {