Skip to content

Commit 27e2935

Browse files
committed
fix: string escape detection in util.ts
closes #45
1 parent 123f074 commit 27e2935

File tree

2 files changed

+16
-1
lines changed

2 files changed

+16
-1
lines changed

src/util.ts

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,12 @@ export type TomlValue = TomlPrimitive | TomlValue[] | TomlTable
3636
export type TomlTableWithoutBigInt = { [key: string]: TomlValueWithoutBigInt }
3737
export type TomlValueWithoutBigInt = Exclude<TomlPrimitive, bigint> | TomlValueWithoutBigInt[] | TomlTableWithoutBigInt
3838

39+
function isEscaped(str: string, ptr: number) {
40+
let i = 0
41+
while (str[ptr - ++i] === '\\');
42+
return --i && (i % 2)
43+
}
44+
3945
export function indexOfNewline (str: string, start = 0, end = str.length) {
4046
let idx = str.indexOf('\n', start)
4147
if (str[idx - 1] === '\r') idx--
@@ -102,7 +108,7 @@ export function getStringEnd (str: string, seek: number) {
102108

103109
seek += target.length - 1
104110
do seek = str.indexOf(target, ++seek)
105-
while (seek > -1 && first !== "'" && str[seek - 1] === '\\' && (str[seek - 2] !== '\\' || str[seek - 3] === '\\'))
111+
while (seek > -1 && first !== "'" && isEscaped(str, seek))
106112

107113
if (seek > -1) {
108114
seek += target.length

test/parse.test.ts

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,15 @@ it('handles escapes in strings', () => {
5757
// Reference: https://github.com/squirrelchat/smol-toml/issues/37
5858
expect(parse('key = "value \\\\\\" value"')).toStrictEqual({ key: 'value \\" value' })
5959
expect(parse('key = "value \\\\\\\\\\" value"')).toStrictEqual({ key: 'value \\\\" value' })
60+
61+
// Reference: https://github.com/squirrelchat/smol-toml/issues/45
62+
expect(parse('key = "\\\\"')).toStrictEqual({ key: '\\' })
63+
expect(parse('key = "\\\\\\\\"')).toStrictEqual({ key: '\\\\' })
64+
expect(parse('key = "\\\\\\\\\\\\"')).toStrictEqual({ key: '\\\\\\' })
65+
66+
expect(parse('key = ["\\\\"]')).toStrictEqual({ key: [ '\\' ] })
67+
expect(parse('key = ["\\\\\\\\"]')).toStrictEqual({ key: [ '\\\\' ] })
68+
expect(parse('key = ["\\\\\\\\\\\\"]')).toStrictEqual({ key: [ '\\\\\\' ] })
6069
})
6170

6271
it('rejects unspecified values', () => {

0 commit comments

Comments
 (0)