markdown-it-cjk-friendly 1.3.2 → 2.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +7 -4
- package/dist/index.d.ts +4 -3
- package/dist/index.js +76 -83
- package/package.json +7 -9
package/README.md
CHANGED
|
@@ -2,6 +2,9 @@
|
|
|
2
2
|
|
|
3
3
|
[](https://npmjs.com/package/markdown-it-cjk-friendly)  [](https://npmjs.com/package/markdown-it-cjk-friendly) [](https://npmjs.com/package/markdown-it-cjk-friendly) [](https://socket.dev/npm/package/markdown-it-cjk-friendly) [](https://snyk.io/advisor/npm-package/markdown-it-cjk-friendly)
|
|
4
4
|
|
|
5
|
+
> [!NOTE]
|
|
6
|
+
> for Socket's diagnostics, please also refer to [that of markdown-it](https://socket.dev/npm/package/markdown-it).
|
|
7
|
+
|
|
5
8
|
A [markdown-it](https://github.com/markdown-it/markdown-it) plugin to make Markdown emphasis (`**`) in CommonMark compatible with Chinese, Japanese, and Korean (CJK).
|
|
6
9
|
|
|
7
10
|
<span lang="ja">CommonMarkの強調記号(`**`)を日本語・中国語・韓国語にきちんと対応させるための[markdown-it](https://github.com/markdown-it/markdown-it)プラグイン</span>
|
|
@@ -90,13 +93,13 @@ Additionally, if you are creating Markdown-related software or services primaril
|
|
|
90
93
|
|
|
91
94
|
## Runtime Requirements / <span lang="ja">実行環境の要件</span> / <span lang="zh-Hans-CN">运行环境要求</span> / <span lang="ko">업데이트 전략</span>
|
|
92
95
|
|
|
93
|
-
This package is ESM-only. It requires Node.js
|
|
96
|
+
This package is ESM-only. It requires Node.js 18 or later. (I have only tested it on 20 and later. There is no factor that would prevent it from working on 18, but I do not guarantee its operation on 18.)
|
|
94
97
|
|
|
95
|
-
<span lang="ja">本パッケージはESM専用です。Node.js
|
|
98
|
+
<span lang="ja">本パッケージはESM専用です。Node.js 18以上が必要です。(動作検証は20以降でのみ行っています。18での動作を妨げる要因はありませんが、動作の保証はありません)</span>
|
|
96
99
|
|
|
97
|
-
<span lang="zh-Hans-CN">此包仅支持ESM。需要Node.js
|
|
100
|
+
<span lang="zh-Hans-CN">此包仅支持ESM。需要Node.js 18或更高版本。(我只测试了20及以后的版本。没有因素会阻止它在18上工作,但我不保证在18上的操作。)</span>
|
|
98
101
|
|
|
99
|
-
<span lang="ko"
|
|
102
|
+
<span lang="ko">본 패키지는 ESM 전용입니다. Node.js 18 이상이 필요합니다. (동작 검증은 20 이후 버전에서만 수행했습니다. 18에서 동작을 방해하는 요인은 없으나, 동작을 보장하지는 않습니다)</span>
|
|
100
103
|
|
|
101
104
|
## Installation / <span lang="ja">インストール</span> / <span lang="zh-Hans-CN">安装</span> / <span lang="ko">설치</span>
|
|
102
105
|
|
package/dist/index.d.ts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
|
-
import MarkdownIt from
|
|
1
|
+
import MarkdownIt from "markdown-it";
|
|
2
2
|
|
|
3
|
+
//#region src/index.d.ts
|
|
3
4
|
declare function markdownItCjkFriendlyPlugin(md: MarkdownIt): void;
|
|
4
|
-
|
|
5
|
-
export { markdownItCjkFriendlyPlugin as default };
|
|
5
|
+
//#endregion
|
|
6
|
+
export { markdownItCjkFriendlyPlugin as default };
|
package/dist/index.js
CHANGED
|
@@ -1,98 +1,91 @@
|
|
|
1
|
-
// src/index.ts
|
|
2
1
|
import { eastAsianWidthType } from "get-east-asian-width";
|
|
3
|
-
import {
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
isWhiteSpace
|
|
7
|
-
} from "markdown-it/lib/common/utils.mjs";
|
|
2
|
+
import { isMdAsciiPunct, isPunctChar, isWhiteSpace } from "markdown-it/lib/common/utils.mjs";
|
|
3
|
+
|
|
4
|
+
//#region src/index.ts
|
|
8
5
|
function isEmoji(uc) {
|
|
9
|
-
|
|
6
|
+
return /^\p{Emoji_Presentation}/u.test(String.fromCodePoint(uc));
|
|
10
7
|
}
|
|
8
|
+
/**
|
|
9
|
+
* Check if `uc` is CJK. Deferred (returns `null`) if IVS.
|
|
10
|
+
*
|
|
11
|
+
* @param uc code point
|
|
12
|
+
* @returns `true` if `uc` is CJK, `false` if not, `null` if IVS
|
|
13
|
+
*/
|
|
11
14
|
function isCjkBase(uc) {
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
case "narrow":
|
|
22
|
-
return false;
|
|
23
|
-
case "ambiguous":
|
|
24
|
-
return null;
|
|
25
|
-
case "neutral":
|
|
26
|
-
return /^\p{sc=Hangul}/u.test(String.fromCodePoint(uc));
|
|
27
|
-
}
|
|
15
|
+
if (uc < 4352) return false;
|
|
16
|
+
switch (eastAsianWidthType(uc)) {
|
|
17
|
+
case "fullwidth":
|
|
18
|
+
case "halfwidth": return true;
|
|
19
|
+
case "wide": return !isEmoji(uc);
|
|
20
|
+
case "narrow": return false;
|
|
21
|
+
case "ambiguous": return null;
|
|
22
|
+
case "neutral": return /^\p{sc=Hangul}/u.test(String.fromCodePoint(uc));
|
|
23
|
+
}
|
|
28
24
|
}
|
|
29
25
|
function is2PreviousCjk(uc, prev) {
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
26
|
+
return isCjkBase(uc) ?? (prev === 65025 && isQuotationMark(uc));
|
|
27
|
+
function isQuotationMark(uc$1) {
|
|
28
|
+
return uc$1 === 8216 || uc$1 === 8217 || uc$1 === 8220 || uc$1 === 8221;
|
|
29
|
+
}
|
|
34
30
|
}
|
|
35
31
|
function isPreviousCjk(uc) {
|
|
36
|
-
|
|
32
|
+
return isCjkBase(uc) ?? (917760 <= uc && uc <= 917999);
|
|
37
33
|
}
|
|
38
34
|
function isNextCjk(uc) {
|
|
39
|
-
|
|
35
|
+
return isCjkBase(uc) ?? false;
|
|
40
36
|
}
|
|
41
37
|
function nonEmojiGeneralUseVS(uc) {
|
|
42
|
-
|
|
38
|
+
return uc >= 65024 && uc <= 65038;
|
|
43
39
|
}
|
|
44
40
|
function markdownItCjkFriendlyPlugin(md) {
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
}
|
|
93
|
-
}
|
|
94
|
-
md.inline.State = CjFriendlyState;
|
|
41
|
+
const PreviousState = md.inline.State;
|
|
42
|
+
class CjkFriendlyState extends PreviousState {
|
|
43
|
+
scanDelims(start, canSplitWord) {
|
|
44
|
+
const max = this.posMax;
|
|
45
|
+
const marker = this.src.charCodeAt(start);
|
|
46
|
+
const [lastChar, lastCharPos] = getLastCharCode(this.src, start);
|
|
47
|
+
let lastMainChar = lastChar;
|
|
48
|
+
let twoPrevChar = null;
|
|
49
|
+
if (nonEmojiGeneralUseVS(lastChar)) {
|
|
50
|
+
twoPrevChar = getLastCharCode(this.src, lastCharPos)[0];
|
|
51
|
+
if (!/^\p{Zs}/u.test(String.fromCodePoint(twoPrevChar))) lastMainChar = twoPrevChar;
|
|
52
|
+
}
|
|
53
|
+
let pos = start;
|
|
54
|
+
while (pos < max && this.src.charCodeAt(pos) === marker) pos++;
|
|
55
|
+
const count = pos - start;
|
|
56
|
+
const nextChar = pos < max ? this.src.codePointAt(pos) : 32;
|
|
57
|
+
const isLastWhiteSpace = isWhiteSpace(lastMainChar);
|
|
58
|
+
const isNextWhiteSpace = isWhiteSpace(nextChar);
|
|
59
|
+
if (isLastWhiteSpace || isNextWhiteSpace) return {
|
|
60
|
+
can_open: !isNextWhiteSpace,
|
|
61
|
+
can_close: !isLastWhiteSpace,
|
|
62
|
+
length: count
|
|
63
|
+
};
|
|
64
|
+
const isLastPunctChar = isMdAsciiPunct(lastMainChar) || isPunctChar(String.fromCodePoint(lastMainChar));
|
|
65
|
+
const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCodePoint(nextChar));
|
|
66
|
+
let left_flanking = isLastPunctChar;
|
|
67
|
+
let right_flanking = isNextPunctChar;
|
|
68
|
+
if (canSplitWord) {
|
|
69
|
+
const isEitherCJKChar = isNextCjk(nextChar) || (twoPrevChar !== null ? is2PreviousCjk(twoPrevChar, lastChar) : isPreviousCjk(lastChar));
|
|
70
|
+
left_flanking ||= isEitherCJKChar || !isNextPunctChar;
|
|
71
|
+
right_flanking ||= isEitherCJKChar || !isLastPunctChar;
|
|
72
|
+
}
|
|
73
|
+
return {
|
|
74
|
+
can_open: left_flanking,
|
|
75
|
+
can_close: right_flanking,
|
|
76
|
+
length: count
|
|
77
|
+
};
|
|
78
|
+
function getLastCharCode(str, pos$1) {
|
|
79
|
+
if (pos$1 <= 0) return [32, -1];
|
|
80
|
+
const charCode = str.charCodeAt(pos$1 - 1);
|
|
81
|
+
if ((charCode & 64512) !== 56320) return [charCode, pos$1 - 1];
|
|
82
|
+
const codePoint = str.codePointAt(pos$1 - 2);
|
|
83
|
+
return codePoint > 65535 ? [codePoint, pos$1 - 2] : [charCode, pos$1 - 1];
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
md.inline.State = CjkFriendlyState;
|
|
95
88
|
}
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
};
|
|
89
|
+
|
|
90
|
+
//#endregion
|
|
91
|
+
export { markdownItCjkFriendlyPlugin as default };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "markdown-it-cjk-friendly",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "2.0.0",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"exports": {
|
|
6
6
|
".": {
|
|
@@ -46,18 +46,16 @@
|
|
|
46
46
|
}
|
|
47
47
|
},
|
|
48
48
|
"dependencies": {
|
|
49
|
-
"get-east-asian-width": "^1.
|
|
49
|
+
"get-east-asian-width": "^1.4.0"
|
|
50
50
|
},
|
|
51
51
|
"engines": {
|
|
52
|
-
"node": ">=
|
|
52
|
+
"node": ">=18"
|
|
53
53
|
},
|
|
54
54
|
"scripts": {
|
|
55
|
-
"build": "
|
|
56
|
-
"build:lib": "
|
|
57
|
-
"
|
|
58
|
-
"dev": "
|
|
59
|
-
"dev:lib": "tsup --watch",
|
|
60
|
-
"dev:rslib": "rslib build --watch",
|
|
55
|
+
"build": "tsdown",
|
|
56
|
+
"build:lib": "tsdown",
|
|
57
|
+
"dev": "tsdown --watch",
|
|
58
|
+
"dev:lib": "tsdown --watch",
|
|
61
59
|
"test": "vitest run",
|
|
62
60
|
"test:lib": "vitest run",
|
|
63
61
|
"test:up": "vitest -u",
|