From 546f6a9a9f256c8b76b0dddb6ef63b0f89518fca Mon Sep 17 00:00:00 2001 From: Josh Goebel Date: Tue, 5 May 2020 10:43:28 -0400 Subject: [PATCH 1/4] fix(javascript) fix regex inside parens after a non-regex --- CHANGES.md | 1 + src/languages/javascript.js | 8 +++++++- src/lib/regex.js | 4 ++++ 3 files changed, 12 insertions(+), 1 deletion(-) diff --git a/CHANGES.md b/CHANGES.md index e5e293e3e2..4d68893e74 100644 --- a/CHANGES.md +++ b/CHANGES.md @@ -14,6 +14,7 @@ Deprecations: Language Improvements: +- fix(javascript) fix regex inside parens after a non-regex (#2530) [Josh Goebel][] - [enh] Add `OPTIMIZE:` and `HACK:` to the labels highlighted inside comments [Josh Goebel][] - enh(typescript/javascript/coffeescript/livescript) derive ECMAscript keywords from a common foudation (#2518) [Josh Goebel][] - enh(typescript) add setInterval, setTimeout, clearInterval, clearTimeout (#2514) [Josh Goebel][] diff --git a/src/languages/javascript.js b/src/languages/javascript.js index 9f900569c2..599c18d9a6 100644 --- a/src/languages/javascript.js +++ b/src/languages/javascript.js @@ -6,6 +6,7 @@ Website: https://developer.mozilla.org/en-US/docs/Web/JavaScript */ import * as ECMAScript from "./lib/ecmascript"; +import * as regex from "../lib/regex"; export default function(hljs) { var FRAGMENT = { @@ -148,7 +149,12 @@ export default function(hljs) { hljs.C_BLOCK_COMMENT_MODE, NUMBER, { // object attr container - begin: /[{,\n]\s*/, relevance: 0, + begin: regex.concat(/[{,\n]\s*/, + // we need to look ahead to make sure that we actually have an + // attribute coming up so we don't steal a comma from a potential + // "value" container + regex.lookahead(IDENT_RE + '\\s*:')), + relevance: 0, contains: [ { begin: IDENT_RE + '\\s*:', returnBegin: true, diff --git a/src/lib/regex.js b/src/lib/regex.js index 003dc9cbca..80a9ce1b70 100644 --- a/src/lib/regex.js +++ b/src/lib/regex.js @@ -8,6 +8,10 @@ export function source(re) { return (re && re.source) || re; } +export function lookahead(regex) { + return concat('(?=', regex, ')'); +} + export function concat(...args) { const joined = args.map((x) => source(x)).join(""); return joined; From 71cf34973476b72c90ed4cfef7c8f568a41e7f99 Mon Sep 17 00:00:00 2001 From: Josh Goebel Date: Tue, 5 May 2020 15:05:18 -0400 Subject: [PATCH 2/4] make the object attr container smarter --- src/languages/javascript.js | 13 +++++++++---- test/markup/javascript/object-attr.expect.txt | 1 + test/markup/javascript/object-attr.txt | 1 + 3 files changed, 11 insertions(+), 4 deletions(-) diff --git a/src/languages/javascript.js b/src/languages/javascript.js index 599c18d9a6..2f97c7afd7 100644 --- a/src/languages/javascript.js +++ b/src/languages/javascript.js @@ -153,14 +153,19 @@ export default function(hljs) { // we need to look ahead to make sure that we actually have an // attribute coming up so we don't steal a comma from a potential // "value" container - regex.lookahead(IDENT_RE + '\\s*:')), + regex.lookahead(regex.concat( + // we also need to allow for multiple possible comments inbetween + // the first key:value pairing + /(\/\/.*\s*)*/, + IDENT_RE + '\\s*:'))), relevance: 0, contains: [ { - begin: IDENT_RE + '\\s*:', returnBegin: true, + className: 'attr', + begin: IDENT_RE + regex.lookahead('\\s*:'), relevance: 0, - contains: [{className: 'attr', begin: IDENT_RE, relevance: 0}] - } + }, + hljs.C_LINE_COMMENT_MODE, ] }, { // "value" container diff --git a/test/markup/javascript/object-attr.expect.txt b/test/markup/javascript/object-attr.expect.txt index e92b578cea..3a8df7eabc 100644 --- a/test/markup/javascript/object-attr.expect.txt +++ b/test/markup/javascript/object-attr.expect.txt @@ -1,6 +1,7 @@ { key: value, // with comment key2: value, + key2clone: value, 'key-3': value, key4: false ? undefined : true } diff --git a/test/markup/javascript/object-attr.txt b/test/markup/javascript/object-attr.txt index 442c0a17ae..078ff8f734 100644 --- a/test/markup/javascript/object-attr.txt +++ b/test/markup/javascript/object-attr.txt @@ -1,6 +1,7 @@ { key: value, // with comment key2: value, + key2clone: value, 'key-3': value, key4: false ? undefined : true } From 007a2a390da3f84cf9c58cce9df4a5c87fdb8ea6 Mon Sep 17 00:00:00 2001 From: Josh Goebel Date: Tue, 5 May 2020 15:20:45 -0400 Subject: [PATCH 3/4] deal with multi-line comments also --- src/languages/javascript.js | 9 ++++++++- test/markup/javascript/object-attr.expect.txt | 4 +++- test/markup/javascript/object-attr.txt | 4 +++- 3 files changed, 14 insertions(+), 3 deletions(-) diff --git a/src/languages/javascript.js b/src/languages/javascript.js index 2f97c7afd7..e7c2f60a34 100644 --- a/src/languages/javascript.js +++ b/src/languages/javascript.js @@ -153,10 +153,18 @@ export default function(hljs) { // we need to look ahead to make sure that we actually have an // attribute coming up so we don't steal a comma from a potential // "value" container + // + // NOTE: this might not work how you think. We don't actually always + // enter this mode and stay. Instead it might merely match `, + // ` and then immediately end after the , because it + // fails to find any actual attrs. But this still does the job because + // it prevents the value contain rule from grabbing this instead and + // prevening this rule from firing when we actually DO have keys. regex.lookahead(regex.concat( // we also need to allow for multiple possible comments inbetween // the first key:value pairing /(\/\/.*\s*)*/, + /(\/\*.*\*\/\s*)*/, IDENT_RE + '\\s*:'))), relevance: 0, contains: [ @@ -165,7 +173,6 @@ export default function(hljs) { begin: IDENT_RE + regex.lookahead('\\s*:'), relevance: 0, }, - hljs.C_LINE_COMMENT_MODE, ] }, { // "value" container diff --git a/test/markup/javascript/object-attr.expect.txt b/test/markup/javascript/object-attr.expect.txt index 3a8df7eabc..87d69747a1 100644 --- a/test/markup/javascript/object-attr.expect.txt +++ b/test/markup/javascript/object-attr.expect.txt @@ -3,5 +3,7 @@ key2: value, key2clone: value, 'key-3': value, - key4: false ? undefined : true + key4: false ? undefined : true, + key5: value, /* with a multiline comment */ + key6: value, } diff --git a/test/markup/javascript/object-attr.txt b/test/markup/javascript/object-attr.txt index 078ff8f734..ade0553d19 100644 --- a/test/markup/javascript/object-attr.txt +++ b/test/markup/javascript/object-attr.txt @@ -3,5 +3,7 @@ key2: value, key2clone: value, 'key-3': value, - key4: false ? undefined : true + key4: false ? undefined : true, + key5: value, /* with a multiline comment */ + key6: value, } From 5136de78d01b47c3ef5d26985b38688ffa9edaf5 Mon Sep 17 00:00:00 2001 From: Josh Goebel Date: Wed, 6 May 2020 23:06:12 -0400 Subject: [PATCH 4/4] comments in any order, spanning multiple lines --- src/languages/javascript.js | 3 +-- test/markup/javascript/object-attr.expect.txt | 5 +++++ test/markup/javascript/object-attr.txt | 6 ++++++ 3 files changed, 12 insertions(+), 2 deletions(-) diff --git a/src/languages/javascript.js b/src/languages/javascript.js index e7c2f60a34..465e81cd44 100644 --- a/src/languages/javascript.js +++ b/src/languages/javascript.js @@ -163,8 +163,7 @@ export default function(hljs) { regex.lookahead(regex.concat( // we also need to allow for multiple possible comments inbetween // the first key:value pairing - /(\/\/.*\s*)*/, - /(\/\*.*\*\/\s*)*/, + /(((\/\/.*)|(\/\*(.|\n)*\*\/))\s*)*/, IDENT_RE + '\\s*:'))), relevance: 0, contains: [ diff --git a/test/markup/javascript/object-attr.expect.txt b/test/markup/javascript/object-attr.expect.txt index 87d69747a1..54e9d7301f 100644 --- a/test/markup/javascript/object-attr.expect.txt +++ b/test/markup/javascript/object-attr.expect.txt @@ -6,4 +6,9 @@ key4: false ? undefined : true, key5: value, /* with a multiline comment */ key6: value, + key7: value, /* with a multiline comment */ // another comment + key8: value, + key9: value, /* with a REAL multiline +comment */ + key10: value, } diff --git a/test/markup/javascript/object-attr.txt b/test/markup/javascript/object-attr.txt index ade0553d19..b024927090 100644 --- a/test/markup/javascript/object-attr.txt +++ b/test/markup/javascript/object-attr.txt @@ -6,4 +6,10 @@ key4: false ? undefined : true, key5: value, /* with a multiline comment */ key6: value, + key7: value, /* with a multiline comment */ // another comment + key8: value, + key9: value, /* with a REAL multiline +comment */ + key10: value, } +