Skip to content

Commit

Permalink
fix: #3073 function format not escaping control characters and doub…
Browse files Browse the repository at this point in the history
…le quotes in strings
  • Loading branch information
josdejong committed Oct 18, 2023
1 parent 4703c85 commit 66fc3e1
Show file tree
Hide file tree
Showing 3 changed files with 26 additions and 19 deletions.
32 changes: 14 additions & 18 deletions src/utils/string.js
Original file line number Diff line number Diff line change
Expand Up @@ -86,7 +86,7 @@ function _format (value, options) {
}

if (isString(value)) {
return '"' + value + '"'
return stringify(value)
}

if (typeof value === 'function') {
Expand All @@ -101,7 +101,7 @@ function _format (value, options) {
return value.toString(options)
} else {
const entries = Object.keys(value).map(key => {
return '"' + key + '": ' + format(value[key], options)
return stringify(key) + ': ' + format(value[key], options)
})

return '{' + entries.join(', ') + '}'
Expand All @@ -122,28 +122,24 @@ export function stringify (value) {
let escaped = ''
let i = 0
while (i < text.length) {
let c = text.charAt(i)

if (c === '\\') {
escaped += c
i++

c = text.charAt(i)
if (c === '' || '"\\/bfnrtu'.indexOf(c) === -1) {
escaped += '\\' // no valid escape character -> escape it
}
escaped += c
} else if (c === '"') {
escaped += '\\"'
} else {
escaped += c
}
const c = text.charAt(i)
escaped += (c in controlCharacters) ? controlCharacters[c] : c
i++
}

return '"' + escaped + '"'
}

const controlCharacters = {
'"': '\\"',
'\\': '\\\\',
'\b': '\\b',
'\f': '\\f',
'\n': '\\n',
'\r': '\\r',
'\t': '\\t'
}

/**
* Escape special HTML characters
* @param {*} value
Expand Down
3 changes: 2 additions & 1 deletion test/unit-tests/expression/node/ConstantNode.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -138,6 +138,7 @@ describe('ConstantNode', function () {
assert.deepStrictEqual(new ConstantNode(math.bignumber('1e500')).toString(), '1e+500')
assert.deepStrictEqual(new ConstantNode(math.fraction(2, 3)).toString(), '2/3')
assert.strictEqual(new ConstantNode('hi').toString(), '"hi"')
assert.strictEqual(new ConstantNode('with " double quote').toString(), '"with \\" double quote"')
assert.strictEqual(new ConstantNode(true).toString(), 'true')
assert.strictEqual(new ConstantNode(false).toString(), 'false')
assert.strictEqual(new ConstantNode(undefined).toString(), 'undefined')
Expand Down Expand Up @@ -218,6 +219,6 @@ describe('ConstantNode', function () {
it('should escape strings in toTex', function () {
const n = new ConstantNode('space tab\tunderscore_bla$/')

assert.strictEqual(n.toTex(), '\\mathtt{"space~tab\\qquad{}underscore\\_bla\\$/"}')
assert.strictEqual(n.toTex(), '\\mathtt{"space~tab\\textbackslash{}tunderscore\\_bla\\$/"}')
})
})
10 changes: 10 additions & 0 deletions test/unit-tests/utils/string.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,11 @@ describe('string', function () {
assert.strictEqual(format('string'), '"string"')
})

it('should format a string with escape characters', function () {
assert.strictEqual(format('with " double quote'), '"with \\" double quote"')
assert.strictEqual(format('with \\ backslash'), '"with \\\\ backslash"')
})

it('should format an object', function () {
const obj = {
a: 1.1111,
Expand All @@ -81,6 +86,11 @@ describe('string', function () {
assert.strictEqual(format(obj, 3), '{"a": 1.11, "b": 2.22 + 3i}')
})

it('should format an object with escape characters', function () {
assert.strictEqual(format({ 'with " double quote': 42 }), '{"with \\" double quote": 42}')
assert.strictEqual(format({ 'with \\ backslash': 42 }), '{"with \\\\ backslash": 42}')
})

it('should format an object with its own format function', function () {
const obj = {
format: function (options) {
Expand Down

0 comments on commit 66fc3e1

Please sign in to comment.