Browse Source

Merge pull request #7023 from weseek/imprv/support-multibyte-characters-with-growi-directive

imprv: Support multibyte characters with growi-directive
Yuki Takei 3 years ago
parent
commit
f780096201

+ 27 - 12
packages/remark-growi-plugin/src/micromark-extension-growi-plugin/lib/factory-attributes.js

@@ -82,13 +82,6 @@ export function factoryAttributes(
       return shortcutStart(code);
     }
 
-    if (code === codes.colon || code === codes.underscore || code === codes.slash || asciiAlpha(code)) {
-      effects.enter(attributeType);
-      effects.enter(attributeNameType);
-      effects.consume(code);
-      return name;
-    }
-
     if (disallowEol && markdownSpace(code)) {
       return factorySpace(effects, between, types.whitespace)(code);
     }
@@ -97,6 +90,19 @@ export function factoryAttributes(
       return factoryAttributesDevider(effects, between)(code);
     }
 
+    if (code !== codes.rightParenthesis
+      && code !== codes.eof
+      && code !== codes.carriageReturn
+      && code !== codes.lineFeed
+      && code !== codes.carriageReturnLineFeed
+      && code !== codes.ampersand
+    ) {
+      effects.enter(attributeType);
+      effects.enter(attributeNameType);
+      effects.consume(code);
+      return name;
+    }
+
     return end(code);
   }
 
@@ -166,11 +172,20 @@ export function factoryAttributes(
   /** @type {State} */
   function name(code) {
     if (
-      code === codes.dash
-      || code === codes.dot
-      || code === codes.colon
-      || code === codes.underscore
-      || asciiAlphanumeric(code)
+      code !== codes.eof
+        && code !== codes.carriageReturn
+        && code !== codes.lineFeed
+        && code !== codes.carriageReturnLineFeed
+        && code !== codes.quotationMark
+        && code !== codes.numberSign
+        && code !== codes.apostrophe
+        && code !== codes.dot
+        && code !== codes.lessThan
+        && code !== codes.equalsTo
+        && code !== codes.greaterThan
+        && code !== codes.graveAccent
+        && code !== codes.rightParenthesis
+        && code !== codes.space
     ) {
       effects.consume(code);
       return name;

+ 69 - 2
packages/remark-growi-plugin/test/micromark-extension-growi-plugin.test.js

@@ -113,7 +113,7 @@ test('micromark-extension-directive (syntax)', (t) => {
     t.equal(
       micromark('$a(', options()),
       '<p>(</p>',
-      'should support a name followed by an unclosed `{`',
+      'should support a name followed by an unclosed `(`',
     );
 
     t.equal(
@@ -125,7 +125,7 @@ test('micromark-extension-directive (syntax)', (t) => {
     t.equal(
       micromark('$a(b', options()),
       '<p>(b</p>',
-      'should support a name followed by an unclosed `{` w/ content',
+      'should support a name followed by an unclosed `(` w/ content',
     );
 
     t.equal(
@@ -326,6 +326,12 @@ test('micromark-extension-directive (syntax)', (t) => {
       'should not support a grave accent in an unquoted attribute value',
     );
 
+    t.equal(
+      micromark('a $a(b💚=a💚b)', options()),
+      '<p>a </p>',
+      'should support most other characters in attribute keys',
+    );
+
     t.equal(
       micromark('a $a(b=a💚b)', options()),
       '<p>a </p>',
@@ -547,6 +553,12 @@ test('micromark-extension-directive (syntax)', (t) => {
     //   'should not support `=` to start an unquoted attribute value',
     // );
 
+    t.equal(
+      micromark('$a(b💚=a💚b)', options()),
+      '',
+      'should support most other characters in attribute keys',
+    );
+
     t.equal(
       micromark('$a(b=a💚b)', options()),
       '',
@@ -772,6 +784,41 @@ test('micromark-extension-directive (compile)', (t) => {
     'should support directives (youtube)',
   );
 
+  t.equal(
+    micromark(
+      [
+        'Text:',
+        'a $lsx',
+        'a $lsx()',
+        'a $lsx(num=1)',
+        'a $lsx(/)',
+        'a $lsx(💚)',
+        'Leaf:',
+        '$lsx',
+        '$lsx()',
+        '$lsx(num=1)',
+        '$lsx(/)',
+        '$lsx(💚)',
+      ].join('\n\n'),
+      options({ lsx }),
+    ),
+    [
+      '<p>Text:</p>',
+      '<p>a <lsx ></lsx></p>',
+      '<p>a <lsx ></lsx></p>',
+      '<p>a <lsx num="1"></lsx></p>',
+      '<p>a <lsx prefix="/"></lsx></p>',
+      '<p>a <lsx prefix="💚"></lsx></p>',
+      '<p>Leaf:</p>',
+      '<lsx ></lsx>',
+      '<lsx ></lsx>',
+      '<lsx num="1"></lsx>',
+      '<lsx prefix="/"></lsx>',
+      '<lsx prefix="💚"></lsx>',
+    ].join('\n'),
+    'should support directives (lsx)',
+  );
+
   t.equal(
     micromark('a $youtube[Cat in a box]\n$br a', options({ youtube, '*': h })),
     '<p>a <youtube>Cat in a box</youtube>\n<br> a</p>',
@@ -1051,6 +1098,26 @@ function youtube(d) {
   this.tag('</iframe>');
 }
 
+/** @type {Handle} */
+function lsx(d) {
+  const attrs = d.attributes || {};
+
+  const props = [];
+
+  // eslint-disable-next-line no-restricted-syntax
+  for (const key in attrs) {
+    if (attrs[key].length === 0) {
+      props.push(`prefix="${key}"`);
+    }
+    else {
+      props.push(`${key}="${attrs[key]}"`);
+    }
+  }
+
+  this.tag(`<lsx ${props.join(' ')}>`);
+  this.tag('</lsx>');
+}
+
 /** @type {Handle} */
 function h(d) {
   const content = d.content || d.label;